/* * Copyright (c) 2013, WSO2 Inc. (http://www.wso2.org) All Rights Reserved. * * WSO2 Inc. licenses this file to you under the Apache License, * Version 2.0 (the "License"); you may not use this file except * in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, * software distributed under the License is distributed on an * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY * KIND, either express or implied. See the License for the * specific language governing permissions and limitations * under the License. */ package org.wso2.carbon.identity.application.authentication.framework.model; import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletRequestWrapper; import java.io.UnsupportedEncodingException; import java.net.URLEncoder; import java.util.ArrayList; import java.util.Collections; import java.util.Enumeration; import java.util.List; import java.util.Map; import java.util.TreeMap; /** * This class is used as a wrapper to the incoming http request to authentication framework. * On the arrival of a request to authentication endpoint. The request will be wrapped from this * wrapper with all the information in the AuthenticationRequestCache */ public class AuthenticationFrameworkWrapper extends HttpServletRequestWrapper { private static final Log log = LogFactory.getLog(AuthenticationFrameworkWrapper.class); // Map which keeps parameters from authentication request cache private final Map<String, String[]> modifiableParameters; // This map keeps headers which are appended from cache entry private final Map<String, String> modifiableHeaders; // This map will contain all the parameters including cache params and original req params private Map<String, String[]> allParameters = null; /** * Create a new request wrapper that will merge additional parameters into * the request object without prematurely reading parameters from the * original request. * * @param request HttpServletRequest * @param additionalParams All Query Params * @param additionalHeaders All Headers */ public AuthenticationFrameworkWrapper(final HttpServletRequest request, final Map<String, String[]> additionalParams, final Map<String, String> additionalHeaders) { super(request); modifiableParameters = new TreeMap<String, String[]>(); modifiableParameters.putAll(additionalParams); modifiableHeaders = new TreeMap<String, String>(); modifiableHeaders.putAll(additionalHeaders); } @Override public String getParameter(final String name) { String[] strings = getParameterMap().get(name); if (strings != null) { return strings[0]; } return super.getParameter(name); } @Override public String getHeader(String name) { String header = super.getHeader(name); return (header != null) ? header : modifiableHeaders.get(name); } /** * Will return header names which were in original request and will append * all the header names which were in authentication request cache entry */ @Override public Enumeration<String> getHeaderNames() { List<String> list = new ArrayList<String>(); for (Enumeration<String> headerNames = super.getHeaderNames(); headerNames. hasMoreElements(); ) { list.add(headerNames.nextElement()); } for (String keys : modifiableHeaders.keySet()) { list.add(keys); } return Collections.enumeration(list); } /** * Will return params which were in original request and will append * all the params which were in authentication request cache entry */ @Override public Map<String, String[]> getParameterMap() { if (allParameters == null) { allParameters = new TreeMap<String, String[]>(); allParameters.putAll(super.getParameterMap()); allParameters.putAll(modifiableParameters); } //Return an unmodifiable collection because we need to uphold the interface contract. return Collections.unmodifiableMap(allParameters); } @Override public Enumeration<String> getParameterNames() { return Collections.enumeration(getParameterMap().keySet()); } @Override public String[] getParameterValues(final String name) { return getParameterMap().get(name); } /** * Will construct the new query parameter with the params */ @Override public String getQueryString() { StringBuilder sb = new StringBuilder(); for (Map.Entry<String, String[]> entry : getParameterMap().entrySet()) { if (sb.length() > 0) { sb.append('&'); } try { sb.append(URLEncoder.encode(entry.getKey(), "UTF-8")) .append('=') .append(URLEncoder.encode(entry.getValue()[0], "UTF-8")); } catch (UnsupportedEncodingException e) { log.error("Error while encoding query string built using entry key : " + entry. getKey() + " and value : " + entry.getValue()[0], e); } } return sb.toString(); } /** * Adds a header to the wrapper object * * @param key Key of the header * @param values Value of the header */ public void addHeader(String key, String values) { modifiableHeaders.put(key, values); } }