/**
* Copyright 2014 55 Minutes (http://www.55minutes.com)
*
* Licensed 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 fiftyfive.wicket.util;
import java.util.ArrayList;
import java.util.Enumeration;
import java.util.List;
import java.util.Map;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.wicket.protocol.http.servlet.ServletWebRequest;
import org.apache.wicket.request.Url;
import org.apache.wicket.request.cycle.RequestCycle;
import org.apache.wicket.util.string.Strings;
/**
* Provides easy access to the HTTP information that triggered the current
* Wicket request. Wicket normally hides this information from us, but
* occassionally we need access to things like the raw URL or HTTP headers.
* Note that these methods only work when called within a Wicket thread.
*
* @since 2.0
*/
public class HttpUtils
{
/**
* Returns the {@link HttpServletRequest} associated with the current
* Wicket request, or {@code null} one cannot be found.
*/
public static HttpServletRequest getHttpServletRequest()
{
Object req = RequestCycle.get().getRequest().getContainerRequest();
if(req instanceof HttpServletRequest)
{
return (HttpServletRequest) req;
}
return null;
}
/**
* Returns the {@link HttpServletResponse} associated with the current
* Wicket request, or {@code null} one cannot be found.
*/
public static HttpServletResponse getHttpServletResponse()
{
Object resp = RequestCycle.get().getResponse().getContainerResponse();
if(resp instanceof HttpServletResponse)
{
return (HttpServletResponse) resp;
}
return null;
}
/**
* Returns the value of the {@code User-Agent} HTTP header, as provided
* by the {@link HttpServletRequest}. May be {@code null}.
*/
public static String getUserAgent()
{
HttpServletRequest http = getHttpServletRequest();
return null == http ? null : http.getHeader("User-Agent");
}
/**
* Returns all HTTP headers as key-value pairs. Since headers can be listed
* more than once, it is possible that a header key can have multiple
* values. The resulting List may be empty, but never {@code null}.
*/
public static List<Map.Entry<String,String>> getHeaders()
{
List<Map.Entry<String,String>> headers;
headers = new ArrayList<Map.Entry<String,String>>();
HttpServletRequest http = getHttpServletRequest();
if(http != null)
{
for(Enumeration n=http.getHeaderNames(); n.hasMoreElements();)
{
String name = (String) n.nextElement();
for(Enumeration v=http.getHeaders(name); v.hasMoreElements();)
{
headers.add(new Header(name, (String) v.nextElement()));
}
}
}
return headers;
}
/**
* Returns the entire URL that was used to render the current page,
* which should match what the user sees in the browser location bar.
* Includes protocol, host, port absolute path and query string.
* <p>
* <b>If the current request is an ajax one, this URL will not match
* the actual ajax HTTP request being handled by the server.</b> Instead
* this URL will be most recent non-ajax request, as observed in the
* browser location bar.
*
* @see org.apache.wicket.request.Request#getClientUrl
* @since 3.0
*/
public static String getAbsolutePageUrl()
{
String absolute = null;
RequestCycle rc = RequestCycle.get();
Url url = rc.getRequest().getClientUrl();
HttpServletRequest http = getHttpServletRequest();
if(url != null && http != null)
{
ServletWebRequest webRequest = (ServletWebRequest) rc.getRequest();
String port = ":" + http.getServerPort();
if(http.getServerPort() == 80 && http.getScheme().equals("http"))
{
port = "";
}
absolute = Strings.join("/",
http.getScheme() + "://" + http.getServerName() + port,
http.getServerName(),
http.getContextPath(),
webRequest.getFilterPrefix(),
url.toString()
);
}
return absolute;
}
/**
* Returns the entire URL that was used to make the current request,
* including protocol, host, port, absolute path and query string.
* May return {@code null} if the current request is not an HTTP one.
* <p>
* <b>Note that if the current request is an ajax one, this URL will be
* different from the URL that the user sees in the browser location
* bar.</b>
*/
public static String getAbsoluteRequestUrl()
{
HttpServletRequest request = getHttpServletRequest();
if(null == request) return null;
StringBuffer url = request.getRequestURL();
String query = request.getQueryString();
if(query != null)
{
url.append("?");
url.append(query);
}
return url.toString();
}
/**
* Returns the Wicket portion of the URL that was used to make the current
* request, including relative path and query string. The protocol, host,
* port, and base Wicket path are not included.
* <p>
* <b>Note that if the current request is an ajax one, this URL will be
* different from the URL that the user sees in the browser location
* bar.</b>
*/
public static String getRelativeRequestUrl()
{
return RequestCycle.get().getRequest().getUrl().toString();
}
/**
* Not meant to be instantiated.
*/
private HttpUtils()
{
super();
}
/**
* An immutable key-value pair.
*/
private static class Header implements Map.Entry<String,String>
{
private String key;
private String value;
private Header(String key, String value)
{
this.key = key;
this.value = value;
}
public String getKey()
{
return this.key;
}
public String getValue()
{
return this.value;
}
public String setValue(String value)
{
throw new UnsupportedOperationException();
}
}
}