001: /* ====================================================================
002: * The Jcorporate Apache Style Software License, Version 1.2 05-07-2002
003: *
004: * Copyright (c) 1995-2002 Jcorporate Ltd. All rights reserved.
005: *
006: * Redistribution and use in source and binary forms, with or without
007: * modification, are permitted provided that the following conditions
008: * are met:
009: *
010: * 1. Redistributions of source code must retain the above copyright
011: * notice, this list of conditions and the following disclaimer.
012: *
013: * 2. Redistributions in binary form must reproduce the above copyright
014: * notice, this list of conditions and the following disclaimer in
015: * the documentation and/or other materials provided with the
016: * distribution.
017: *
018: * 3. The end-user documentation included with the redistribution,
019: * if any, must include the following acknowledgment:
020: * "This product includes software developed by Jcorporate Ltd.
021: * (http://www.jcorporate.com/)."
022: * Alternately, this acknowledgment may appear in the software itself,
023: * if and wherever such third-party acknowledgments normally appear.
024: *
025: * 4. "Jcorporate" and product names such as "Expresso" must
026: * not be used to endorse or promote products derived from this
027: * software without prior written permission. For written permission,
028: * please contact info@jcorporate.com.
029: *
030: * 5. Products derived from this software may not be called "Expresso",
031: * or other Jcorporate product names; nor may "Expresso" or other
032: * Jcorporate product names appear in their name, without prior
033: * written permission of Jcorporate Ltd.
034: *
035: * 6. No product derived from this software may compete in the same
036: * market space, i.e. framework, without prior written permission
037: * of Jcorporate Ltd. For written permission, please contact
038: * partners@jcorporate.com.
039: *
040: * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
041: * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
042: * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
043: * DISCLAIMED. IN NO EVENT SHALL JCORPORATE LTD OR ITS CONTRIBUTORS
044: * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
045: * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
046: * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
047: * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
048: * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
049: * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
050: * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
051: * SUCH DAMAGE.
052: * ====================================================================
053: *
054: * This software consists of voluntary contributions made by many
055: * individuals on behalf of the Jcorporate Ltd. Contributions back
056: * to the project(s) are encouraged when you make modifications.
057: * Please send them to support@jcorporate.com. For more information
058: * on Jcorporate Ltd. and its products, please see
059: * <http://www.jcorporate.com/>.
060: *
061: * Portions of this software are based upon other open source
062: * products and are subject to their respective licenses.
063: */
064: package com.jcorporate.expresso.core.controller;
065:
066: import com.jcorporate.expresso.core.controller.session.HTTPPersistentSession;
067: import com.jcorporate.expresso.core.i18n.Messages;
068: import com.jcorporate.expresso.core.jsdkapi.GenericSession;
069: import com.jcorporate.expresso.core.misc.CurrentLogin;
070: import com.jcorporate.expresso.core.misc.StringUtil;
071: import com.jcorporate.expresso.core.misc.URLUTF8Encoder;
072: import com.jcorporate.expresso.core.misc.upload.FileItem;
073: import com.jcorporate.expresso.core.security.User;
074: import org.apache.log4j.Logger;
075: import org.apache.struts.action.ActionForm;
076: import org.apache.struts.action.ActionMapping;
077: import org.apache.struts.upload.MultipartRequestHandler;
078:
079: import javax.servlet.Servlet;
080: import javax.servlet.ServletException;
081: import javax.servlet.ServletRequest;
082: import javax.servlet.ServletResponse;
083: import javax.servlet.http.HttpServletRequest;
084: import javax.servlet.http.HttpServletResponse;
085: import javax.servlet.http.HttpSession;
086: import java.util.Enumeration;
087: import java.util.Hashtable;
088: import java.util.Locale;
089: import java.util.StringTokenizer;
090: import java.util.Vector;
091:
092: /**
093: * ServletControllerRequest is an extension of ControllerRequest that also contains
094: * access to "special" servlet-related items, such as the ServletResponse object.
095: * It should only be used *when absolutely necessary*, as normally a standard ControllerParms
096: * object is better.
097: */
098: public class ServletControllerRequest extends ControllerRequest
099: implements Cloneable {
100: private static Logger log = Logger
101: .getLogger(ServletControllerRequest.class);
102:
103: /**
104: * NOTE: The response object below should be used VERY RARELY. It is not good
105: * Controller design to simply send output to this stream for response data
106: * that could be represented as Outputs, Inputs, etc. It is here for those
107: * situations where a controller must take servlet-API specific actions,
108: * such as setting a custom mime type or sending a binary stream of data back to
109: * the client. Don't use it if you don't *need* it.
110: */
111: private ServletResponse myServletResponse = null;
112: private ServletRequest myServletRequest = null;
113: private Servlet myCallingServlet = null;
114: private ActionMapping myMapping = null;
115: private ActionForm myForm = null;
116:
117: /**
118: * Default constructor
119: */
120: public ServletControllerRequest() {
121:
122: } /* ServletControllerRequest() */
123:
124: /**
125: * Sets the servlet response object
126: *
127: * @param newResponse the new servlet response
128: * @see #getServletResponse
129: */
130: public synchronized void setServletResponse(
131: ServletResponse newResponse) {
132: myServletResponse = newResponse;
133: }
134:
135: /**
136: * Sets the servlet request object
137: *
138: * @param newRequest the new servlet request
139: * @see #getServletRequest
140: */
141: public synchronized void setServletRequest(ServletRequest newRequest) {
142: myServletRequest = newRequest;
143: }
144:
145: /**
146: * Sets the calling servlet. For example an ExpressoActionServlet
147: *
148: * @param newServlet the new calling servlet
149: * @see #getCallingServlet
150: */
151: public void setCallingServlet(Servlet newServlet) {
152: myCallingServlet = newServlet;
153: }
154:
155: /**
156: * Gets the calling servlet. Used for creation, for example.
157: *
158: * @return javax.servlet.Servlet set previously in setCallingServlet()
159: * @see #getCallingServlet
160: */
161: public Servlet getCallingServlet() {
162: return myCallingServlet;
163: }
164:
165: /**
166: * Sets the action mapping as a convenience for pure Struts writer
167: * <p> author Peter Pilgrim
168: *
169: * @param newMapping the ActionMapping associated with the controller request
170: * @see #getMapping
171: */
172: public synchronized void setMapping(ActionMapping newMapping) {
173: this .myMapping = newMapping;
174: }
175:
176: /**
177: * Gets the action mapping as a convenience for pure Struts writer.
178: * The base <code>Controller</code> object stores the current
179: * action mapping instance in the <code>ControllerResponse</code>
180: * using this method. Writers who only ever intend there
181: * controller to be used in a web environment can access the
182: * action mapping to do more sophisticated processing.
183: * <p/>
184: * <pre>
185: * public AcmeController extends DBController {
186: * <p/>
187: * protected void runProcessOrderState(
188: * ControllerRequest req,
189: * ControllerRequest res )
190: * {
191: * ServletControllerRequest request =
192: * (ServletControllerRequest)req;
193: * ActionMapping mapping = request.getMapping();
194: * <p/>
195: * }
196: * ...
197: * }
198: * </pre>
199: * <p/>
200: * author Peter Pilgrim
201: *
202: * @return ActionMapping
203: * @see #setMapping
204: */
205: public synchronized ActionMapping getMapping() {
206: return myMapping;
207: }
208:
209: /**
210: * Sets the action form as a convenience for pure Struts writer.
211: * <p/>
212: * author Peter Pilgrim Fri Jan 23 23:40:14 GMT 2004
213: *
214: * @param newForm the ActionForm associated with the controller request
215: * @see #getForm
216: */
217: public synchronized void setForm(ActionForm newForm) {
218: this .myForm = newForm;
219: }
220:
221: /**
222: * Gets the action form as a convenience for pure Struts writer.
223: * The base <code>Controller</code> object stores the current
224: * action form instance in the <code>ControllerResponse</code>
225: * using this method. Writers who only ever intend there
226: * controller to be used in a web environment can access the
227: * action form to do more sophisticated processing.
228: * <p/>
229: * <pre>
230: * public AcmeController extends DBController {
231: * <p/>
232: * protected void runProcessOrderState(
233: * ControllerRequest req,
234: * ControllerRequest res )
235: * {
236: * ServletControllerRequest request =
237: * (ServletControllerRequest)req;
238: * ActionForm form = request.getForm();
239: * <p/>
240: * }
241: * ...
242: * }
243: * </pre>
244: * <p/>
245: * author Peter Pilgrim
246: *
247: * @return ActionForm
248: * @see #setForm
249: */
250: public synchronized ActionForm getForm() {
251: return myForm;
252: }
253:
254: /**
255: * Gets the servlet request object
256: * <p/>
257: * <p/>
258: * Important: A Controller should only use this method if strictly necessary, and not
259: * write output that is otherwise able to be handled with inputs, outputs and transitions.
260: * If you do access the response object, you must also call setCustomOutput(true) in the
261: * ControllResponse object to let the Controller container (ControllerServlet, ControllRun, etc)
262: * know that it should not attempt to handle view processing itself.
263: * Don't use it if you don't *need* it.
264: * </p>
265: *
266: * @return ServletRequest object
267: * @see #getServletResponse
268: * @see #setServletRequest
269: */
270: public ServletRequest getServletRequest() {
271: return myServletRequest;
272: }
273:
274: /**
275: * Gets the servlet response object
276: * <p/>
277: * <p/>
278: * Important: A Controller should only use this method if strictly necessary, and not
279: * write output that is otherwise able to be handled with inputs, outputs and transitions.
280: * If you do access the response object, you must also call setCustomOutput(true) in the
281: * ControllResponse object to let the Controller container (ControllerServlet, ControllRun, etc)
282: * know that it should not attempt to handle view processing itself.
283: * Don't use it if you don't *need* it.
284: * </p>
285: *
286: * @return ServletResponse object
287: * @see #getServletRequest
288: * @see #setServletResponse
289: */
290: public ServletResponse getServletResponse() {
291: return myServletResponse;
292: }
293:
294: /**
295: * Gets the http servlet response object
296: * <p/>
297: * <p/>
298: * Important: A Controller should only use this method if strictly necessary, and not
299: * write output that is otherwise able to be handled with inputs, outputs and transitions.
300: * If you do access the response object, you must also call setCustomOutput(true) in the
301: * ControllResponse object to let the Controller container (ControllerServlet, ControllRun, etc)
302: * know that it should not attempt to handle view processing itself.
303: * Don't use it if you don't *need* it.
304: * </p>
305: *
306: * @return HttpServletRequest object
307: * @throws ClassCastException if the servlet request cannot be
308: * convert to <code>HttpServletResponse</code>
309: * @see #getHttpServletResponse
310: */
311: public HttpServletRequest getHttpServletRequest() {
312: return (HttpServletRequest) myServletRequest;
313: }
314:
315: /**
316: * Gets the http servlet response object
317: * <p/>
318: * <p/>
319: * Important: A Controller should only use this method if strictly necessary, and not
320: * write output that is otherwise able to be handled with inputs, outputs and transitions.
321: * If you do access the response object, you must also call setCustomOutput(true) in the
322: * ControllResponse object to let the Controller container (ControllerServlet, ControllRun, etc)
323: * know that it should not attempt to handle view processing itself.
324: * Don't use it if you don't *need* it.
325: * </p>
326: *
327: * @return HttpServletResponse object
328: * @throws ClassCastException if the servlet request cannot be
329: * convert to <code>HttpServletResponse</code>
330: * @see #getHttpServletRequest
331: */
332: public HttpServletResponse getHttpServletResponse() {
333: return (HttpServletResponse) myServletResponse;
334: }
335:
336: /**
337: * Return a Hashtable of parameter name/parameter value pairs. If the parameter
338: * is a file upload, then the parameter value is not a string, it's a Vector of
339: * two strings - the first is the value of the parameter as usual, the second
340: * is the file name that the file was uploaded into in the temporary directory.
341: *
342: * @param req the servlet request
343: * @param controller the controller being referenced
344: * @return Hashtable of keys Strings mapped to values (String/String)
345: * @throws ControllerException upon error
346: * @throws IllegalArgumentException if any parameters are null
347: */
348: private static Hashtable parseParamsReq(HttpServletRequest req,
349: Controller controller) throws ControllerException {
350: if (controller == null) {
351: throw new IllegalArgumentException(
352: "ServletControllerRequest."
353: + "parseParamsReq(): Parameter 'controller' must not be null");
354: }
355:
356: String controllerName = controller.getClass().getName();
357: Hashtable params = new Hashtable();
358: params.put(Controller.CONTROLLER_PARAM_KEY, controllerName);
359:
360: if (req == null) {
361: throw new IllegalArgumentException(
362: "Request may not be null here");
363: }
364:
365: String oneName = null;
366: String oneValue = null;
367: log.debug("Regular query string Parameters:");
368:
369: for (Enumeration e = req.getParameterNames(); e
370: .hasMoreElements();) {
371: oneName = (String) e.nextElement();
372: oneValue = StringUtil.notNull(req.getParameter(oneName));
373: params.put(oneName, oneValue);
374:
375: if (log.isDebugEnabled()) {
376: log.debug("Parameter '" + oneName + "', value '"
377: + oneValue + "'");
378: }
379: } /* for each parameter */
380:
381: log.debug("End regular query string parameters");
382:
383: Hashtable newParams = addButtonParams(params);
384:
385: return newParams;
386: // return addDefaultParams(newParams, req, controller);
387: } /* parseParamsReq */
388:
389: /**
390: * Add any parameters specified by the "button"
391: *
392: * @param params the hashtable of parameters to add
393: * @return Hashtable
394: */
395: private static Hashtable addButtonParams(Hashtable params)
396: throws ControllerException {
397: log.debug("Adding button parameters");
398:
399: String oneParamName = null;
400: Object oneParamValue = null;
401: boolean gotControllerFromButton = false;
402: boolean gotStateFromButton = false;
403: Hashtable newParams = new Hashtable();
404:
405: for (Enumeration e = params.keys(); e.hasMoreElements();) {
406: oneParamName = (String) e.nextElement();
407: oneParamValue = params.get(oneParamName);
408:
409: // This param name/vale should be added to the list as is
410: boolean addThisParam = true;
411:
412: // Handle special cases
413: if (oneParamName.equals(Controller.CONTROLLER_PARAM_KEY)
414: && gotControllerFromButton) {
415:
416: // This is a controller name, but we already have one
417: // previously set from a button (xxx_params).
418: addThisParam = false;
419:
420: } else if (oneParamName.equals(Controller.STATE_PARAM_KEY)
421: && gotStateFromButton) {
422:
423: // This is a state name, but we already have one
424: // previously set from a button (xxx_params).
425: addThisParam = false;
426: } else if (oneParamName.endsWith("_params")) {
427:
428: //This is a button paramter-list
429: String buttonName = oneParamName.substring(0,
430: oneParamName.indexOf("_params"));
431:
432: //Check to see if it is already URL-encoded
433: if (!"u".equals(params.get(buttonName + "_encoding"))) {
434:
435: //It's not encoded, so we do it here and add the encoded version
436: newParams.put(oneParamName, URLUTF8Encoder
437: .encode((String) oneParamValue));
438:
439: // Now indicate that the just added parameter was URL-encoded
440: newParams.put(buttonName + "_encoding", "u");
441:
442: // We added it, no need to add it again....
443: addThisParam = false;
444: }
445: }
446: // If we passed special-cases check above, then add the param name/value
447: if (addThisParam) {
448: newParams.put(oneParamName, oneParamValue);
449: }
450: if (oneParamName.startsWith("button_")) {
451:
452: //We add a special parameter to the collection, which
453: //is simply "button"="name_ofButton"
454: String buttonName = oneParamName.substring(oneParamName
455: .indexOf("_") + 1);
456:
457: /**
458: * button names come in from the browser like
459:
460: button_promptLogin.y
461: button_promptLogin.x
462:
463: cut off those .x, .y trailers
464: */
465: if (buttonName.endsWith(".x")) {
466: buttonName = buttonName.substring(0, buttonName
467: .length() - 2);
468: }
469: if (buttonName.endsWith(".y")) {
470: buttonName = buttonName.substring(0, buttonName
471: .length() - 2);
472: }
473:
474: if (log.isDebugEnabled()) {
475: log.debug("There is a button parameter called '"
476: + buttonName + "'");
477: }
478:
479: newParams.put("button", buttonName);
480:
481: /* pick up the corresponding parameter string, if any */
482: String paramString = (String) params.get(buttonName
483: + "_params");
484:
485: if (paramString != null) {
486: log.debug("Button parameters:");
487:
488: //We first check to see if the button parameters string is encoded. If it is, we decode it
489: //before parsing it.
490: String encodeType = (String) params.get(buttonName
491: + "_encoding");
492:
493: if ("u".equals(encodeType)) {
494:
495: //this param string has been URL encoded
496: paramString = URLUTF8Encoder
497: .decode(paramString);
498: } /* if the param string for the button was encoded */
499:
500: /* parse it into a hashtable */
501: StringTokenizer stkpm = null;
502: stkpm = new StringTokenizer(paramString, "&");
503:
504: while (stkpm.hasMoreTokens()) {
505: String pairValue = stkpm.nextToken();
506:
507: //This decode is paired up with the getParamString() method's encode() in
508: //the Transition class.
509: pairValue = URLUTF8Encoder.decode(pairValue);
510:
511: String paramName = pairValue;
512: String paramValue = "";
513: int position = pairValue.indexOf("=");
514: if (position != -1) {
515: paramName = pairValue
516: .substring(0, position);
517: position++; //ignore the '='
518: if (position < pairValue.length()) {
519: paramValue = pairValue
520: .substring(position);
521: }
522: }
523:
524: newParams.put(paramName, paramValue);
525:
526: if (paramName
527: .equals(Controller.CONTROLLER_PARAM_KEY)) {
528: gotControllerFromButton = true;
529: } else if (paramName
530: .equals(Controller.STATE_PARAM_KEY)) {
531: gotStateFromButton = true;
532: }
533:
534: if (log.isDebugEnabled()) {
535: log.debug("Parameter '" + paramName
536: + "', value '" + paramValue + "'");
537: }
538: } /* while more parameters in the button param string */
539:
540: log.debug("End button parameters");
541: } else { /* if the button param string exists */
542: throw new ControllerException("Button '"
543: + buttonName + "' was clicked, but no "
544: + "button parameters field called '"
545: + buttonName + "_params' was found.");
546: }
547: } /* if this param is a buitton */
548:
549: } /* for each of the parameters */
550:
551: return newParams;
552: }
553:
554: /**
555: * Static constructor for creating an servlet controller request
556: * with all the <em>acoutrements</em> of the Struts Action execution signature.
557: * <p/>
558: * <p/>
559: * I deliberate add the <code>ActionMapping</code>, <code>ActionForm beans</code>
560: * as conveniences for Struts developers. You can probably sense I am cheesed off like
561: * Simon Cowell int American (Pop) Idol
562: * <p/>
563: * <p/>
564: * Docu byte Peter Pilgrim Fri Jan 23 23:20:41 GMT 2004
565: *
566: * @param mapping The ActionMapping used to select this instance
567: * @param form The optional ActionForm bean for this request (if any)
568: * @param request the Servlet Request
569: * @param response the Servlet Response
570: * @param controller the Controller
571: * @throws ControllerException exception upon controller error
572: * @throws ServletException upon javax.servlet related errors
573: */
574: public static ServletControllerRequest parseParamsMultiPart(
575: MultipartRequestHandler mp, ActionMapping mapping,
576: ActionForm form, HttpServletRequest request,
577: HttpServletResponse response, Controller controller)
578: throws ServletException, ControllerException {
579: String controllerName = controller.getClass().getName();
580:
581: //set up the required parameters
582: ServletControllerRequest cparams = new ServletControllerRequest();
583: cparams.setMapping(mapping);
584: cparams.setForm(form);
585: cparams.setParameters(null);
586:
587: Hashtable params = new Hashtable();
588: params.put(Controller.CONTROLLER_PARAM_KEY, controllerName);
589:
590: Hashtable textParams = mp.getTextElements();
591: Hashtable fileParams = mp.getFileElements();
592: String oneKey = null;
593:
594: for (Enumeration te = textParams.keys(); te.hasMoreElements();) {
595: oneKey = (String) te.nextElement();
596: params.put(oneKey, textParams.get(oneKey));
597: log.debug("Got '" + oneKey + "', '"
598: + (String) textParams.get(oneKey) + "'");
599: }
600: for (Enumeration fe = fileParams.keys(); fe.hasMoreElements();) {
601: oneKey = (String) fe.nextElement();
602:
603: FileItem oneFileItem = (FileItem) fileParams.get(oneKey);
604: Vector oneFile = new Vector();
605: oneFile.addElement(oneFileItem.getFileName());
606: oneFile
607: .addElement(oneFileItem.getStoreLocation()
608: .getPath());
609: params.put(oneKey, oneFile);
610: log.debug("Got file '" + oneKey + "', file '"
611: + oneFileItem.getFileName() + "'");
612: }
613:
614: HttpSession session = request.getSession(false);
615: String userName = null;
616: int uid = 0;
617:
618: if (session != null) {
619: Object o = GenericSession.getAttribute(request,
620: "CurrentLogin");
621:
622: if (o != null) {
623: CurrentLogin cl = (CurrentLogin) o;
624: uid = cl.getUid();
625: userName = cl.getUserName();
626:
627: if (log.isDebugEnabled()) {
628: log.debug("Login established as user '" + userName
629: + "', uid " + uid);
630: }
631: } else {
632: log
633: .debug("No CurrentLogin object in session - assuming 'none'");
634: }
635: } else {
636: userName = User.UNKNOWN_USER;
637: }
638:
639: cparams.setUser(userName);
640: cparams.setUid(uid);
641:
642: /* Hand the controller a place to store it's persistent values */
643: cparams
644: .setSession(new HTTPPersistentSession(request, response));
645: cparams.setServletRequest(request);
646: cparams.setServletResponse(response);
647: cparams.setDataContext(getDBName(request));
648:
649: // Hashtable newParams = addButtonParams(params);
650: // Hashtable finalParams = addDefaultParams(newParams, request,
651: // controller);
652: Hashtable finalParams = addButtonParams(params);
653: Object oneParamValue = null;
654: String oneParamName = null;
655:
656: for (Enumeration ep = finalParams.keys(); ep.hasMoreElements();) {
657: oneParamName = (String) ep.nextElement();
658: oneParamValue = finalParams.get(oneParamName);
659:
660: if (oneParamValue instanceof String) {
661: cparams.setParameter(oneParamName,
662: (String) oneParamValue);
663: } else if (oneParamValue instanceof Vector) {
664: Vector v = (Vector) oneParamValue;
665: Enumeration ee = v.elements();
666: String clientFileName = (String) ee.nextElement();
667: String serverFileName = (String) ee.nextElement();
668: cparams.setFileParameter(oneParamName, clientFileName,
669: serverFileName);
670: }
671: } /* for each parameter */
672:
673: return cparams;
674: } /* parseParamsMultiPart */
675:
676: /**
677: * Parse a regular servlet request for parameters (e.g. not multipart)
678: *
679: * @param mapping The ActionMapping used to select this instance
680: * @param form The optional ActionForm bean for this request (if any)
681: * @param request the Servlet Request
682: * @param response the Servlet Response
683: * @param controller the Controller
684: * @return a constructed ServletControllerRequest object
685: * @throws ControllerException exception upon controller error
686: * @throws ServletException upon javax.servlet related errors
687: */
688: public static ServletControllerRequest parseParams(
689: ActionMapping mapping, ActionForm form,
690: HttpServletRequest request, HttpServletResponse response,
691: Controller controller) throws ServletException,
692: ControllerException {
693: //set up the required parameters
694: Hashtable params = parseParamsReq(request, controller);
695: HttpSession session = request.getSession(false);
696: ServletControllerRequest cparams = new ServletControllerRequest();
697: cparams.setMapping(mapping);
698: cparams.setForm(form);
699: String userName = null;
700: int uid = 0;
701:
702: if (session != null) {
703: Object o = GenericSession.getAttribute(request,
704: "CurrentLogin");
705:
706: if (o != null) {
707: CurrentLogin cl = (CurrentLogin) o;
708: uid = cl.getUid();
709: userName = cl.getUserName();
710:
711: if (log.isDebugEnabled()) {
712: log.debug("Login established as user '" + userName
713: + "', uid " + uid);
714: }
715: } else {
716: log
717: .debug("No CurrentLogin object in session - assuming 'none'");
718: }
719: } else {
720: userName = User.UNKNOWN_USER;
721: log.debug("No session available - user is none");
722: }
723:
724: cparams.setUser(userName);
725: cparams.setUid(uid);
726:
727: Object oneParamValue = null;
728: String oneParamName = null;
729:
730: //Fixed on 7/11/2001. The line below was added to ensure that
731: //the params collection is regenerated on each request
732: cparams.setParameters(null);
733: boolean newRouting = (request.getAttribute("usedRouting") == null);
734:
735: for (Enumeration ep = params.keys(); ep.hasMoreElements();) {
736: oneParamName = (String) ep.nextElement();
737: oneParamValue = params.get(oneParamName);
738:
739: //Cleanup controller and state params because they have been consumed already.
740: //Not removing them will cause an unintended rerouting in the Controller.perform() method.
741:
742: boolean routingParam = (oneParamName
743: .equals(Controller.CONTROLLER_PARAM_KEY) || oneParamName
744: .equals(Controller.STATE_PARAM_KEY));
745: if (newRouting || (!newRouting && !routingParam)) {
746: if (oneParamValue instanceof String) {
747: cparams.setParameter(oneParamName,
748: (String) oneParamValue);
749: } else if (oneParamValue instanceof Vector) {
750: Vector v = (Vector) oneParamValue;
751: Enumeration ee = v.elements();
752: String clientFileName = (String) ee.nextElement();
753: String serverFileName = (String) ee.nextElement();
754: cparams.setFileParameter(oneParamName,
755: clientFileName, serverFileName);
756: }
757: }
758: } /* for each parameter */
759:
760: /* Hand the controller a place to store it's persistent values */
761: cparams
762: .setSession(new HTTPPersistentSession(request, response));
763: cparams.setServletRequest(request);
764: cparams.setServletResponse(response);
765:
766: cparams.setDataContext(getDBName(request));
767:
768: return cparams;
769: }
770:
771: /**
772: * Convenience method to get the database name out of the session
773: * <p/>
774: * <p/>
775: * <p/>
776: * I deliberate add the <code>ActionMapping</code>, <code>ActionForm beans</code>
777: * as conveniences for Struts developers. You can probably sense I am cheesed off like
778: * Simon Cowell int American (Pop) Idol
779: * <p/>
780: * <p/>
781: * Docu byte Peter Pilgrim Fri Jan 23 23:20:41 GMT 2004
782: *
783: * @param request the servlet request object
784: * @return The name of the specified alternate database
785: */
786: private static String getDBName(HttpServletRequest request) {
787: try {
788: CurrentLogin cl = (CurrentLogin) GenericSession
789: .getAttribute(request, CurrentLogin.LOGIN_KEY);
790:
791: if (cl == null) {
792: return "default";
793: }
794:
795: return cl.getDBName();
796: } catch (ServletException se) {
797: log.error(se);
798:
799: return "default";
800: }
801: } /* getDBName(HttpServletRequest) */
802:
803: public Locale getLocale() {
804: Locale l = null;
805:
806: try {
807: if (myServletRequest != null) {
808: Object o = GenericSession.getAttribute(
809: (HttpServletRequest) myServletRequest,
810: Messages.LOCALE_KEY);
811:
812: if (o != null) {
813: l = (Locale) o;
814: }
815: }
816: } catch (ServletException se) {
817: log.error(se);
818: }
819: if (l == null) {
820: l = Locale.getDefault();
821: }
822:
823: return l;
824: }
825:
826: /**
827: * Method that returns a copy of itself with all the fields properly filled
828: * out. Note that all the servletrequest/servletresponse classes are merely
829: * shallow copied since a deep copy is meaningless in a servlet environment
830: *
831: * @return a new instantiated ServletControllerRequest object
832: */
833: public Object clone() {
834: ServletControllerRequest scr = (ServletControllerRequest) super
835: .clone();
836: scr.myCallingServlet = this .myCallingServlet;
837: scr.myServletRequest = this .myServletRequest;
838: scr.myServletResponse = this .myServletResponse;
839: scr.myMapping = this .myMapping;
840:
841: return scr;
842: }
843:
844: /**
845: * Fetches array of parameter values from underlying HTTP request; use this in a web app to access
846: * the underlying parameters in the HTTP request which have the same name; parameters with the same name are not
847: * reflected in the hashtable of params maintained by ControllerRequest;
848: *
849: * @param paramName key to look for among all parameters
850: * @return an array of String objects containing all of the values the given request parameter has, or null if the parameter does not exist.
851: */
852: public String[] getParamValues(String paramName) {
853: HttpServletRequest hreq = (HttpServletRequest) getServletRequest();
854: return hreq.getParameterValues(paramName);
855: }
856:
857: } /* ServletControllerRequest */
|