001: /*
002: * Licensed to the Apache Software Foundation (ASF) under one or more
003: * contributor license agreements. See the NOTICE file distributed with
004: * this work for additional information regarding copyright ownership.
005: * The ASF licenses this file to You under the Apache License, Version 2.0
006: * (the "License"); you may not use this file except in compliance with
007: * the License. You may obtain a copy of the License at
008: *
009: * http://www.apache.org/licenses/LICENSE-2.0
010: *
011: * Unless required by applicable law or agreed to in writing, software
012: * distributed under the License is distributed on an "AS IS" BASIS,
013: * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014: * See the License for the specific language governing permissions and
015: * limitations under the License.
016: */
017: package org.apache.cocoon.environment.http;
018:
019: import java.io.BufferedReader;
020: import java.io.IOException;
021: import java.io.UnsupportedEncodingException;
022: import java.lang.ref.WeakReference;
023: import java.util.Collections;
024: import java.util.Enumeration;
025: import java.util.HashMap;
026: import java.util.Locale;
027: import java.util.Map;
028: import java.util.Vector;
029: import java.util.WeakHashMap;
030:
031: import javax.servlet.RequestDispatcher;
032: import javax.servlet.ServletInputStream;
033: import javax.servlet.http.HttpServletRequest;
034:
035: import org.apache.avalon.framework.CascadingRuntimeException;
036: import org.apache.cocoon.environment.Cookie;
037: import org.apache.cocoon.environment.Request;
038: import org.apache.cocoon.environment.Session;
039: import org.apache.cocoon.environment.http.HttpSession;
040: import org.apache.cocoon.servlet.multipart.MultipartHttpServletRequest;
041:
042: /**
043: * Implements the {@link org.apache.cocoon.environment.Request} interface
044: * to provide request information in the HTTP servlets environment.
045: *
046: * @author <a href="mailto:giacomo@apache.org">Giacomo Pati</a>
047: * @version $Id: HttpRequest.java 433543 2006-08-22 06:22:54Z crossley $
048: */
049: public final class HttpRequest implements Request {
050:
051: /** The real HttpServletRequest object */
052: private final HttpServletRequest req;
053:
054: /** The HttpEnvironment object */
055: private final HttpEnvironment env;
056:
057: /** The character encoding of parameters */
058: private String form_encoding;
059:
060: /** The default form encoding of the servlet container */
061: private String container_encoding;
062:
063: /** The map to assure 1:1-mapping of server sessions and Cocoon session wrappers */
064: private static final Map sessions = new WeakHashMap();
065:
066: /**
067: * Creates a HttpRequest based on a real HttpServletRequest object
068: */
069: protected HttpRequest(HttpServletRequest req, HttpEnvironment env) {
070: super ();
071: this .req = req;
072: this .env = env;
073: }
074:
075: /* (non-Javadoc)
076: * @see org.apache.cocoon.environment.Request#get(java.lang.String)
077: */
078: public Object get(String name) {
079: // if the request has been wrapped then access its method
080: if (req instanceof MultipartHttpServletRequest) {
081: return ((MultipartHttpServletRequest) req).get(name);
082: } else {
083: String[] values = req.getParameterValues(name);
084: if (values == null) {
085: return null;
086: }
087: if (values.length == 1) {
088: return values[0];
089: }
090: if (values.length > 1) {
091: Vector vect = new Vector(values.length);
092: for (int i = 0; i < values.length; i++) {
093: vect.add(values[i]);
094: }
095: return vect;
096: }
097: }
098: return null;
099: }
100:
101: /* The HttpServletRequest interface methods */
102:
103: public String getAuthType() {
104: return this .req.getAuthType();
105: }
106:
107: private Cookie[] wrappedCookies = null;
108: private Map wrappedCookieMap = null;
109:
110: public Cookie[] getCookies() {
111: if (this .wrappedCookieMap == null) {
112: wrapCookies();
113: }
114: return this .wrappedCookies;
115: }
116:
117: public Map getCookieMap() {
118: if (this .wrappedCookieMap == null) {
119: wrapCookies();
120: }
121: return this .wrappedCookieMap;
122: }
123:
124: private synchronized void wrapCookies() {
125: this .wrappedCookieMap = new HashMap();
126: javax.servlet.http.Cookie[] cookies = this .req.getCookies();
127: if (cookies != null) {
128: this .wrappedCookies = new Cookie[cookies.length];
129: for (int i = 0; i < cookies.length; i++) {
130: HttpCookie cookie = new HttpCookie(cookies[i]);
131: this .wrappedCookies[i] = cookie;
132: this .wrappedCookieMap.put(cookie.getName(), cookie);
133: }
134: }
135: this .wrappedCookieMap = Collections
136: .unmodifiableMap(this .wrappedCookieMap);
137: }
138:
139: public long getDateHeader(String name) {
140: return this .req.getDateHeader(name);
141: }
142:
143: public String getHeader(String name) {
144: return this .req.getHeader(name);
145: }
146:
147: public Enumeration getHeaders(String name) {
148: return this .req.getHeaders(name);
149: }
150:
151: public Enumeration getHeaderNames() {
152: return this .req.getHeaderNames();
153: }
154:
155: public int getIntHeader(String name) {
156: return this .req.getIntHeader(name);
157: }
158:
159: public String getMethod() {
160: return this .req.getMethod();
161: }
162:
163: public String getPathInfo() {
164: return this .req.getPathInfo();
165: }
166:
167: public String getPathTranslated() {
168: return this .req.getPathTranslated();
169: }
170:
171: public String getContextPath() {
172: return this .req.getContextPath();
173: }
174:
175: public String getQueryString() {
176: return this .req.getQueryString();
177: }
178:
179: public String getRemoteUser() {
180: return this .req.getRemoteUser();
181: }
182:
183: public boolean isUserInRole(String role) {
184: return this .req.isUserInRole(role);
185: }
186:
187: public java.security.Principal getUserPrincipal() {
188: return this .req.getUserPrincipal();
189: }
190:
191: public String getRequestedSessionId() {
192: return this .req.getRequestedSessionId();
193: }
194:
195: protected String reqURI;
196:
197: public String getRequestURI() {
198: if (this .reqURI == null) {
199: this .reqURI = this .req.getRequestURI();
200: if (this .reqURI.equals("/")) {
201: String s = this .req.getServletPath();
202: final StringBuffer buffer = new StringBuffer();
203: if (null != s)
204: buffer.append(s);
205: s = this .req.getPathInfo();
206: if (null != s)
207: buffer.append(s);
208: this .reqURI = buffer.toString();
209: }
210: }
211: return this .reqURI;
212: }
213:
214: public String getSitemapURI() {
215: return this .env.getURI();
216: }
217:
218: public String getSitemapURIPrefix() {
219: return this .env.getURIPrefix();
220: }
221:
222: public String getServletPath() {
223: return this .req.getServletPath();
224: }
225:
226: /**
227: * Creates a wrapper implementing {@link Session} for
228: * {@link javax.servlet.http.HttpSession}.
229: * The method must assure 1:1-mapping of
230: * {@link javax.servlet.http.HttpSession}s to Cocoon's session wrappers.
231: *
232: * @see org.apache.cocoon.environment.Request#getSession(boolean)
233: */
234: public Session getSession(boolean create) {
235: javax.servlet.http.HttpSession serverSession = this .req
236: .getSession(create);
237: HttpSession session;
238: if (serverSession != null) {
239: synchronized (sessions) {
240: // retrieve existing wrapper
241: WeakReference ref = (WeakReference) sessions
242: .get(serverSession);
243: if (ref == null
244: || (session = (HttpSession) ref.get()) == null) {
245: // create new wrapper
246: session = new HttpSession(serverSession);
247: sessions.put(serverSession, new WeakReference(
248: session));
249: }
250: }
251: } else {
252: // invalidate
253: session = null;
254: }
255: return session;
256: }
257:
258: public Session getSession() {
259: return this .getSession(true);
260: }
261:
262: public boolean isRequestedSessionIdValid() {
263: return this .req.isRequestedSessionIdValid();
264: }
265:
266: public boolean isRequestedSessionIdFromCookie() {
267: return this .req.isRequestedSessionIdFromCookie();
268: }
269:
270: public boolean isRequestedSessionIdFromURL() {
271: return this .req.isRequestedSessionIdFromURL();
272: }
273:
274: /**
275: * @deprecated As of Version 2.1 of the Java Servlet API, use
276: * {@link #isRequestedSessionIdFromURL()} instead.
277: */
278: public boolean isRequestedSessionIdFromUrl() {
279: return this .req.isRequestedSessionIdFromURL();
280: }
281:
282: /* The ServletRequest interface methods */
283:
284: public Object getAttribute(String name) {
285: return this .req.getAttribute(name);
286: }
287:
288: public Enumeration getAttributeNames() {
289: return this .req.getAttributeNames();
290: }
291:
292: public String getCharacterEncoding() {
293: if (this .form_encoding == null) {
294: return this .req.getCharacterEncoding();
295: } else {
296: return this .form_encoding;
297: }
298: }
299:
300: public void setCharacterEncoding(String form_encoding)
301: throws java.io.UnsupportedEncodingException {
302: this .form_encoding = form_encoding;
303: }
304:
305: /**
306: * Sets the default encoding of the servlet container.
307: */
308: public void setContainerEncoding(String container_encoding) {
309: this .container_encoding = container_encoding;
310: }
311:
312: public int getContentLength() {
313: return this .req.getContentLength();
314: }
315:
316: public String getContentType() {
317: return this .req.getContentType();
318: }
319:
320: public ServletInputStream getInputStream() throws IOException {
321: return this .req.getInputStream();
322: }
323:
324: public String getParameter(String name) {
325: String value = this .req.getParameter(name);
326: if (this .form_encoding == null
327: || this .container_encoding == null || value == null) {
328: return value;
329: }
330: // Form and container encoding are equal, skip expensive value decoding
331: if (this .container_encoding.equals(this .form_encoding)) {
332: return value;
333: }
334: return decode(value);
335: }
336:
337: private String decode(String str) {
338: if (str == null)
339: return null;
340: try {
341: if (this .container_encoding == null)
342: this .container_encoding = "ISO-8859-1";
343: byte[] bytes = str.getBytes(this .container_encoding);
344: return new String(bytes, form_encoding);
345: } catch (UnsupportedEncodingException uee) {
346: throw new CascadingRuntimeException(
347: "Unsupported Encoding Exception", uee);
348: }
349: }
350:
351: public Enumeration getParameterNames() {
352: return this .req.getParameterNames();
353: }
354:
355: public String[] getParameterValues(String name) {
356: String[] values = this .req.getParameterValues(name);
357: if (values == null)
358: return null;
359: if (this .form_encoding == null) {
360: return values;
361: }
362: String[] decoded_values = new String[values.length];
363: for (int i = 0; i < values.length; ++i) {
364: decoded_values[i] = decode(values[i]);
365: }
366: return decoded_values;
367: }
368:
369: public String getProtocol() {
370: return this .req.getProtocol();
371: }
372:
373: public String getScheme() {
374: return this .req.getScheme();
375: }
376:
377: public String getServerName() {
378: return this .req.getServerName();
379: }
380:
381: public int getServerPort() {
382: return this .req.getServerPort();
383: }
384:
385: public BufferedReader getReader() throws IOException {
386: return this .req.getReader();
387: }
388:
389: public String getRemoteAddr() {
390: return this .req.getRemoteAddr();
391: }
392:
393: public String getRemoteHost() {
394: return this .req.getRemoteHost();
395: }
396:
397: public void setAttribute(String name, Object o) {
398: this .req.setAttribute(name, o);
399: }
400:
401: public void removeAttribute(String name) {
402: this .req.removeAttribute(name);
403: }
404:
405: public Locale getLocale() {
406: return this .req.getLocale();
407: }
408:
409: public Enumeration getLocales() {
410: return this .req.getLocales();
411: }
412:
413: public boolean isSecure() {
414: return this .req.isSecure();
415: }
416:
417: public RequestDispatcher getRequestDispatcher(String path) {
418: return this .req.getRequestDispatcher(path);
419: }
420:
421: /**
422: * @deprecated As of Version 2.1 of the Java Servlet API, use
423: * {@link javax.servlet.ServletContext#getRealPath(java.lang.String)}instead.
424: */
425: public String getRealPath(String path) {
426: return this.req.getRealPath(path);
427: }
428: }
|