Docjar: A Java Source and Docuemnt Enginecom.*    java.*    javax.*    org.*    all    new    plug-in

Quick Search    Search Deep

Source code: servletunit/struts/CactusStrutsTestCase.java


1   //  StrutsTestCase - a JUnit extension for testing Struts actions
2   //  within the context of the ActionServlet.
3   //  Copyright (C) 2002 Deryl Seale
4   //
5   //  This library is free software; you can redistribute it and/or
6   //  modify it under the terms of the Apache Software License as
7   //  published by the Apache Software Foundation; either version 1.1
8   //  of the License, or (at your option) any later version.
9   //
10  //  This library is distributed in the hope that it will be useful,
11  //  but WITHOUT ANY WARRANTY; without even the implied warranty of
12  //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13  //  Apache Software Foundation Licens for more details.
14  //
15  //  You may view the full text here: http://www.apache.org/LICENSE.txt
16  
17  package servletunit.struts;
18  
19  import junit.framework.AssertionFailedError;
20  import org.apache.cactus.ServletTestCase;
21  import org.apache.commons.logging.Log;
22  import org.apache.commons.logging.LogFactory;
23  import org.apache.struts.Globals;
24  import org.apache.struts.action.ActionForm;
25  import org.apache.struts.action.ActionServlet;
26  
27  import javax.servlet.ServletContext;
28  import javax.servlet.ServletException;
29  import javax.servlet.ServletConfig;
30  import javax.servlet.http.*;
31  import java.util.Enumeration;
32  import java.util.List;
33  import java.util.ArrayList;
34  import java.util.Iterator;
35  
36  /**
37   * CactusStrutsTestCase is an extension of the Cactus ServletTestCase
38   * base class that provides additional methods to aid in testing
39   * Struts Action objects.  It uses an in-container approach to run
40   * the servlet container, and tests the execution of Action objects as they
41   * are actually run through the Struts ActionServlet.  CactusStrutsTestCase
42   * provides methods that set up the request path, request parameters
43   * for ActionForm subclasses, as well as methods that can verify
44   * that the correct ActionForward was used and that the proper
45   * ActionError messages were supplied.
46   * <br>
47   * <br>
48   * <b>Please note</b> that this class is meant to run in the Cactus
49   * framework, and you must configure your test environment
50   * accordingly.  Please see <a href="http://jakarta.apache.org/cactus">http://jakarta.apache.org/cactus</a>
51   * for more details.
52   *
53   */
54  public class CactusStrutsTestCase extends ServletTestCase {
55  
56      protected ActionServlet actionServlet;
57      protected HttpServletRequestWrapper requestWrapper;
58      protected HttpServletResponseWrapper responseWrapper;
59      protected boolean isInitialized = false;
60      protected boolean actionServletIsInitialized = false;
61      protected boolean requestPathIsSet = false;
62      protected String moduleName;
63      protected String servletMapping = "*.do";
64  
65      protected static Log logger = LogFactory.getLog(CactusStrutsTestCase.class);
66  
67      /**
68       * Default constructor.
69       */
70      public CactusStrutsTestCase() {
71          super();
72      }
73  
74      /**
75       * Constructor that takes test name parameter, for backwards compatibility with older versions on JUnit.
76       */
77      public CactusStrutsTestCase(String testName) {
78          super(testName);
79      }
80  
81      /**
82       * A check that every method should run to ensure that the
83       * base class setUp method has been called.
84       */
85      private void init() {
86          if (!isInitialized) {
87              throw new AssertionFailedError("You are overriding the setUp() method without calling super.setUp().  You must call the superclass setUp() and tearDown() methods in your TestCase subclass to ensure proper initialization.");
88          }
89      }
90  
91      /**
92       * Sets up the test fixture for this test.  This method creates
93       * an instance of the ActionServlet, initializes it to validate
94       * forms and turn off debugging, and clears all other parameters.
95       */
96      protected void setUp() throws Exception {
97          if (logger.isDebugEnabled())
98              logger.debug("Entering");
99          try {
100 
101             if (actionServlet == null)
102                 actionServlet = new ActionServlet();
103             requestWrapper = null;
104             responseWrapper = null;
105             ServletContext servletContext = new StrutsServletContextWrapper(this.config.getServletContext());
106             this.config = new StrutsServletConfigWrapper(this.config);
107             ((StrutsServletConfigWrapper) this.config).setServletContext(servletContext);
108             this.request = new StrutsRequestWrapper(this.request);
109             this.response = new StrutsResponseWrapper(this.response);
110             isInitialized = true;
111             if (logger.isDebugEnabled())
112                 logger.debug("Exiting");
113         } catch (Exception e) {
114             if (logger.isDebugEnabled())
115                 logger.debug(e);
116             throw new AssertionFailedError("Error trying to set up test fixture: " + e.getClass() + " - " + e.getMessage());
117         }
118     }
119 
120     /**
121      * Sets the servlet mapping used to map requests to the Struts controller.  This is used to restore
122      * proper setting after the test has been executed. By default, the stanard "*.do" mapping will be
123      * restored, so only use this method for non-standard servlet mappings.
124      * @param servletMapping
125      */
126     public void setServletMapping(String servletMapping) {
127         this.servletMapping = servletMapping;
128     }
129 
130     protected void tearDown () throws Exception {
131         if (logger.isTraceEnabled())
132             logger.trace("Entering");
133 
134         // remove all RequestProcessor instances from context
135         // so that web application will function normally.
136         ServletContext context = this.config.getServletContext();
137         List nameList = new ArrayList();
138         Enumeration attributeNames = context.getAttributeNames();
139         while (attributeNames.hasMoreElements()) {
140             String name = (String) attributeNames.nextElement();
141             if (name.startsWith(Globals.REQUEST_PROCESSOR_KEY))
142                 nameList.add(name);
143         }
144 
145         // restore the original servlet mapping
146         ServletConfig originalConfig = ((org.apache.cactus.server.ServletConfigWrapper) this.config).getOriginalConfig();
147         ServletContext originalContext = originalConfig.getServletContext();
148         originalContext.setAttribute(Globals.SERVLET_KEY,servletMapping);
149         ((StrutsServletConfigWrapper) config).setServletContext(originalContext);
150 
151 
152         for (Iterator iterator = nameList.iterator(); iterator.hasNext();) {
153             context.removeAttribute((String) iterator.next());
154         }
155 
156         if (logger.isTraceEnabled())
157             logger.trace("Exiting");
158     }
159 
160     /**
161      * Returns an HttpServletRequest object that can be used in
162      * this test.
163      */
164     public HttpServletRequest getRequest() {
165         if (logger.isDebugEnabled())
166             logger.debug("Entering");
167         init();
168         if (logger.isDebugEnabled())
169             logger.debug("Exiting");
170         return this.request;
171     }
172 
173     /**
174      * Returns a HttpServletRequestWrapper object that can be used
175      * in this test. Note that if {@link #setRequestWrapper} has not been
176      * called, this method will return an instance of
177      * javax.servlet.http.HttpServletRequestWrapper.
178      */
179     public HttpServletRequestWrapper getRequestWrapper() {
180         if (logger.isDebugEnabled())
181             logger.debug("Entering");
182         init();
183         if (requestWrapper == null) {
184             if (logger.isDebugEnabled())
185                 logger.debug("Exiting");
186             return new HttpServletRequestWrapper(this.request);
187         } else {
188             if (logger.isDebugEnabled()) {
189                 logger.debug("wrapper class is '" + requestWrapper.getClass() + "'");
190             }
191             if (logger.isDebugEnabled())
192                 logger.debug("Exiting");
193             return requestWrapper;
194         }
195     }
196 
197     /**
198      * Set this TestCase to use a given HttpServletRequestWrapper
199      * class when calling Action.execute().  Note that if this
200      * method is not called, then the normal HttpServletRequest
201      * object is used.
202      *
203      * @param wrapper an HttpServletRequestWrapper object to be
204      * used when calling Action.execute().
205      */
206     public void setRequestWrapper(HttpServletRequestWrapper wrapper) {
207         if (logger.isDebugEnabled())
208             logger.debug("Entering - wrapper = " + wrapper);
209         init();
210         if (wrapper == null) {
211             throw new IllegalArgumentException("wrapper class cannot be null!");
212         } else {
213             if (wrapper.getRequest() == null)
214                 wrapper.setRequest(this.request);
215             this.requestWrapper = wrapper;
216         }
217         if (logger.isDebugEnabled())
218             logger.debug("Exiting");
219     }
220 
221     /**
222      * Returns an HttpServletResponse object that can be used in
223      * this test.
224      */
225     public HttpServletResponse getResponse() {
226         if (logger.isDebugEnabled())
227             logger.debug("Entering");
228         init();
229         if (logger.isDebugEnabled())
230             logger.debug("Exiting");
231         return this.response;
232     }
233 
234     /**
235      * Returns an HttpServletResponseWrapper object that can be used in
236      * this test.  Note that if {@link #setResponseWrapper} has not been
237      * called, this method will return an instance of
238      * javax.servlet.http.HttpServletResponseWrapper.
239      */
240     public HttpServletResponseWrapper getResponseWrapper() {
241         if (logger.isDebugEnabled())
242             logger.debug("Entering");
243         init();
244         if (responseWrapper == null) {
245             if (logger.isDebugEnabled())
246                 logger.debug("Exiting getResponseWrapper()");
247             return new HttpServletResponseWrapper(this.response);
248         } else {
249             if (logger.isDebugEnabled()) {
250                 logger.debug("wrapper class is '" + responseWrapper.getClass() + "'");
251             }
252             if (logger.isDebugEnabled())
253                 logger.debug("getResponseWrapper()");
254             return responseWrapper;
255         }
256     }
257 
258     /**
259      * Set this TestCase to use a given HttpServletResponseWrapper
260      * class when calling Action.execute().  Note that if this
261      * method is not called, then the normal HttpServletResponse
262      * object is used.
263      *
264      * @param wrapper an HttpServletResponseWrapper object to be
265      * used when calling Action.execute().
266      */
267     public void setResponseWrapper(HttpServletResponseWrapper wrapper) {
268         if (logger.isDebugEnabled())
269             logger.debug("Entering - wrapper = " + wrapper.getClass());
270         init();
271         if (wrapper == null)
272             throw new IllegalArgumentException("wrapper class cannot be null!");
273         else {
274             if (wrapper.getResponse() == null)
275                 wrapper.setResponse(this.response);
276             if (logger.isDebugEnabled())
277                 logger.debug("Exiting");
278             this.responseWrapper = wrapper;
279         }
280     }
281 
282     /**
283      * Returns an HttpSession object that can be used in this
284      * test.
285      */
286     public HttpSession getSession() {
287         if (logger.isDebugEnabled())
288             logger.debug("Entering");
289         init();
290         if (logger.isDebugEnabled())
291             logger.debug("Exiting");
292         return this.session;
293     }
294 
295     /**
296      * Adds an HttpServletRequest parameter to be used in setting up the
297      * ActionForm instance to be used in this test.  Each parameter added
298      * should correspond to an attribute in the ActionForm instance used
299      * by the Action instance being tested.
300      */
301     public void addRequestParameter(String parameterName, String parameterValue)
302     {
303         if (logger.isDebugEnabled())
304             logger.debug("Entering - paramaterName = " + parameterName + ", parameterValue = " + parameterValue);
305         init();
306         ((StrutsRequestWrapper) this.request).addParameter(parameterName,parameterValue);
307         if (logger.isDebugEnabled())
308             logger.debug("Exiting");
309     }
310 
311     /**
312      * Adds an HttpServletRequest parameter that is an array of String values
313      * to be used in setting up the ActionForm instance to be used in this test.
314      * Each parameter added should correspond to an attribute in the ActionForm
315      * instance used by the Action instance being tested.
316      */
317     public void addRequestParameter(String parameterName, String[] parameterValues)
318     {
319         if (logger.isDebugEnabled())
320             logger.debug("Entering - paramaterName = " + parameterName + ", parameterValue = " + parameterValues);
321         init();
322         ((StrutsRequestWrapper) this.request).addParameter(parameterName,parameterValues);
323         if (logger.isDebugEnabled())
324             logger.debug("Exiting");
325     }
326 
327     /**
328      * Clears all request parameters previously set.  NOTE: This will <strong>not</strong> clear
329      * parameters set using Cactus beginXXX methods!
330      */
331     public void clearRequestParameters() {
332         init();
333         ((StrutsRequestWrapper) request).clearRequestParameters();
334     }
335 
336     /**
337      * Sets the request path instructing the ActionServlet to used a
338      * particual ActionMapping.
339      *
340      * @param pathInfo the request path to be processed.  This should
341      * correspond to a particular action mapping, as would normally
342      * appear in an HTML or JSP source file.
343      */
344     public void setRequestPathInfo(String pathInfo) {
345         if (logger.isDebugEnabled())
346             logger.debug("Entering - pathInfo = " + pathInfo);
347         init();
348         this.setRequestPathInfo("",pathInfo);
349         if (logger.isDebugEnabled())
350             logger.debug("Exiting");
351     }
352 
353 
354     /**
355      * Sets the request path instructing the ActionServlet to used a
356      * particual ActionMapping.  Also sets the ServletPath property
357      * on the request.
358      *
359      * @param moduleName the name of the Struts sub-application with
360      * which this request is associated, or null if it is the default
361      * application.
362      * @param pathInfo the request path to be processed.  This should
363      * correspond to a particular action mapping, as would normally
364      * appear in an HTML or JSP source file.  If this request is part
365      * of a sub-application, the module name should not appear in the
366      * request path.
367      */
368     public void setRequestPathInfo(String moduleName, String pathInfo) {
369         if (logger.isDebugEnabled())
370             logger.debug("Entering - moduleName = " + moduleName + ", pathInfo = " + pathInfo);
371         init();
372         ((StrutsRequestWrapper) this.request).setPathInfo(Common.stripActionPath(pathInfo));
373         if (moduleName != null) {
374             if (!moduleName.equals("")) {
375                 if (!moduleName.startsWith("/"))
376                     moduleName = "/" + moduleName;
377                 if (!moduleName.endsWith("/"))
378                     moduleName = moduleName + "/";
379             }
380             if (logger.isDebugEnabled()) {
381                 logger.debug("setting request.ServletPath value = " + moduleName);
382             }
383             ((StrutsRequestWrapper) this.request).setServletPath(moduleName);
384             this.requestPathIsSet = true;
385         }
386         if (logger.isDebugEnabled())
387             logger.debug("Exiting");
388     }
389 
390     /**
391      * Sets an initialization parameter on the
392      * ActionServlet.  Allows you to simulate an init parameter
393      * that would normally have been found in web.xml.
394      * @param key the name of the initialization parameter
395      * @param value the value of the intialization parameter
396      */
397     public void setInitParameter(String key, String value){
398         if (logger.isDebugEnabled())
399             logger.debug("Entering -  key = " + key + ", value = " + value);
400         this.config.setInitParameter(key, value);
401         this.actionServletIsInitialized = false;
402         if (logger.isDebugEnabled())
403             logger.debug("Exiting");
404     }
405 
406     /**
407      * Sets the location of the Struts configuration file for the default module.
408      * This method can take either an absolute path, or a relative path.  If an
409      * absolute path is supplied, the configuration file will be loaded from the
410      * underlying filesystem; otherwise, the ServletContext loader will be used.
411      */
412     public void setConfigFile(String pathname) {
413         if (logger.isDebugEnabled())
414             logger.debug("Entering - pathname = " + pathname);
415         init();
416         setConfigFile(null,pathname);
417         if (logger.isDebugEnabled())
418             logger.debug("Exiting");
419     }
420 
421     /**
422      * Sets the struts configuration file for a given sub-application.
423      * This method can take either an absolute path, or a relative path.  If an
424      * absolute path is supplied, the configuration file will be loaded from the
425      * underlying filesystem; otherwise, the ServletContext loader will be used.
426      *
427      * @param moduleName the name of the sub-application, or null if this is the default application
428      * @param pathname the location of the configuration file for this sub-application
429      */
430     public void setConfigFile(String moduleName, String pathname) {
431         if (logger.isDebugEnabled())
432             logger.debug("Entering - moduleName = " + moduleName + ", pathname = " + pathname);
433         init();
434         if (moduleName == null)
435             this.config.setInitParameter("config",pathname);
436         else
437             this.config.setInitParameter("config/" + moduleName,pathname);
438         actionServletIsInitialized = false;
439         if (logger.isDebugEnabled())
440             logger.debug("Exiting");
441     }
442 
443     /**
444      * Returns the ActionServlet controller used in this
445      * test.
446      *
447      */
448     public ActionServlet getActionServlet() {
449         if (logger.isDebugEnabled())
450             logger.debug("Entering");
451         init();
452         try {
453             if (!actionServletIsInitialized) {
454                 // the RequestProcessor holds on to the ServletContext, so
455                 // we need to ensure that it is replaced for each test.
456                 ServletContext context = config.getServletContext();
457                 String name = "org.apache.struts.action.REQUEST_PROCESSOR";
458 
459                 // remove request processor for default module
460                 Object obj = context.getAttribute(name);
461                 if (obj != null) {
462                     config.getServletContext().removeAttribute(name);
463                 }
464 
465                 // remove request processor for sub-applications, if used.
466                 // todo: this seems pretty redundant.. may want to make this cleaner.
467                 String moduleName = request.getServletPath() != null ? request.getServletPath() : "";
468 
469                 if (moduleName.endsWith("/"))
470                     moduleName = moduleName.substring(0,moduleName.lastIndexOf("/"));
471 
472                 obj = context.getAttribute(name + moduleName);
473                 if (obj != null) {
474                     config.getServletContext().removeAttribute(name + moduleName);
475                 }
476 
477                 this.actionServlet.init(config);
478                 actionServletIsInitialized = true;
479             }
480             if (logger.isDebugEnabled())
481                 logger.debug("Exiting");
482             return this.actionServlet;
483         } catch (ServletException e) {
484             if (logger.isDebugEnabled())
485                 logger.debug("Error in getActionServlet()",e.getRootCause());
486             throw new AssertionFailedError("Error while initializing ActionServlet: " + e.getMessage());
487         }
488     }
489 
490     /**
491      * Sets the ActionServlet to be used in this test execution.  This
492      * method should only be used if you plan to use a customized
493      * version different from that provided in the Struts distribution.
494      */
495     public void setActionServlet(ActionServlet servlet) {
496         if (logger.isDebugEnabled())
497             logger.debug("Entering - servlet = " + servlet);
498         init();
499         if (servlet == null)
500             throw new AssertionFailedError("Cannot set ActionServlet to null");
501         this.actionServlet = servlet;
502         actionServletIsInitialized = false;
503         if (logger.isDebugEnabled())
504             logger.debug("Exiting");
505     }
506 
507     /**
508      * Executes the Action instance to be tested.  This method initializes
509      * the ActionServlet, sets up and optionally validates the ActionForm
510      * bean associated with the Action to be tested, and then calls the
511      * Action.execute() method.  Results are stored for further validation.
512      *
513      * @exception AssertionFailedError if there are any execution
514      * errors while calling Action.execute() or ActionForm.validate().
515      *
516      */
517     public void actionPerform() {
518         if (logger.isDebugEnabled())
519             logger.debug("Entering");
520         if(!this.requestPathIsSet){
521             throw new IllegalStateException("You must call setRequestPathInfo() prior to calling actionPerform().");
522         }
523         init();
524         try {
525             HttpServletRequest request = this.request;
526             HttpServletResponse response = this.response;
527             // make sure errors are cleared from last test.
528             request.removeAttribute(Globals.ERROR_KEY);
529             request.removeAttribute(Globals.MESSAGE_KEY);
530 
531             if (this.requestWrapper != null)
532                 request = this.requestWrapper;
533             if (this.responseWrapper != null)
534                 response = this.responseWrapper;
535 
536             ActionServlet actionServlet = this.getActionServlet();
537             actionServlet.doPost(request,response);
538             if (logger.isDebugEnabled())
539                 logger.debug("Exiting");
540         } catch (NullPointerException npe) {
541             String message = "A NullPointerException was thrown.  This may indicate an error in your ActionForm, or "
542                     + "it may indicate that the Struts ActionServlet was unable to find struts config file.  "
543                     + "TestCase is running from " + System.getProperty("user.dir") + " directory.";
544             throw new ExceptionDuringTestError(message, npe);
545         } catch(Exception e){
546             throw new ExceptionDuringTestError("An uncaught exception was thrown during actionExecute()", e);
547         }
548     }
549 
550     /**
551      * Returns the forward sent to RequestDispatcher.
552      */
553     protected String getActualForward() {
554         if (logger.isDebugEnabled())
555             logger.debug("Entering");
556         if (response.containsHeader("Location")) {
557             return Common.stripJSessionID(((StrutsResponseWrapper) response).getRedirectLocation());
558         } else {
559             String forward = ((StrutsServletContextWrapper) this.actionServlet.getServletContext()).getForward();
560             if (logger.isDebugEnabled()) {
561                 logger.debug("actual forward = " + forward);
562             }
563             if (forward == null) {
564                 if (logger.isDebugEnabled())
565                     logger.debug("Exiting");
566                 return null;
567             } else {
568                 String temp = Common.stripJSessionID(forward);
569                 if (!temp.startsWith("/"))
570                     temp = "/" + temp;
571                 String strippedForward = request.getContextPath() + temp;
572                 if (logger.isDebugEnabled()) {
573                     logger.debug("stripped forward and added context path = " + strippedForward);
574                 }
575                 if (logger.isDebugEnabled())
576                     logger.debug("Exiting");
577                 return strippedForward;
578             }
579         }
580 
581     }
582 
583     /**
584      * Verifies if the ActionServlet controller used this forward.
585      *
586      * @param forwardName the logical name of a forward, as defined
587      * in the Struts configuration file.  This can either refer to a
588      * global forward, or one local to the ActionMapping.
589      *
590      * @exception AssertionFailedError if the ActionServlet controller
591      * used a different forward than <code>forwardName</code> after
592      * executing an Action object.
593      */
594     public void verifyForward(String forwardName) throws AssertionFailedError {
595         if (logger.isDebugEnabled())
596             logger.debug("Entering - forwardName = " + forwardName);
597         init();
598         Common.verifyForwardPath(request.getPathInfo(),forwardName,getActualForward(),false,request,config.getServletContext(),config);
599         if (logger.isDebugEnabled())
600             logger.debug("Exiting");
601     }
602 
603     /**
604      * Verifies if the ActionServlet controller used this actual path
605      * as a forward.
606      *
607      * @param forwardPath an absolute pathname to which the request
608      * is to be forwarded.
609      *
610      * @exception AssertionFailedError if the ActionServlet controller
611      * used a different forward path than <code>forwardPath</code> after
612      * executing an Action object.
613      */
614     public void verifyForwardPath(String forwardPath) throws AssertionFailedError {
615         if (logger.isDebugEnabled())
616             logger.debug("Entering - forwardPath = " + forwardPath);
617         init();
618         String actualForward = getActualForward();
619 
620         if ((actualForward == null) && (forwardPath == null)) {
621 // actions can return null forwards.
622             return;
623         }
624 
625         forwardPath = request.getContextPath() + forwardPath;
626 
627         if (actualForward == null) {
628             if (logger.isDebugEnabled()) {
629                 logger.debug("actualForward is null - this usually means it is not mapped properly.");
630             }
631             throw new AssertionFailedError("Was expecting '" + forwardPath + "' but it appears the Action has tried to return an ActionForward that is not mapped correctly.");
632         }
633         if (logger.isDebugEnabled()) {
634             logger.debug("expected forward = '" + forwardPath + "' - actual forward = '" + actualForward + "'");
635         }
636         if (!(actualForward.equals(forwardPath)))
637             throw new AssertionFailedError("was expecting '" + forwardPath + "' but received '" + actualForward + "'");
638         if (logger.isDebugEnabled())
639             logger.debug("Exiting");
640     }
641 
642     /**
643      * Verifies if the ActionServlet controller forwarded to the defined
644      * input path.
645      *
646      * @exception AssertionFailedError if the ActionServlet controller
647      * used a different forward than the defined input path after
648      * executing an Action object.
649      */
650     public void verifyInputForward() {
651         if (logger.isDebugEnabled())
652             logger.debug("Entering");
653         init();
654         Common.verifyForwardPath(request.getPathInfo(),null,getActualForward(),true,request,config.getServletContext(),config);
655         if (logger.isDebugEnabled())
656             logger.debug("Exiting");
657     }
658 
659     /**
660      * Verifies that the ActionServlet controller used this forward and Tiles definition.
661      *
662      * @param forwardName the logical name of a forward, as defined
663      * in the Struts configuration file.  This can either refer to a
664      * global forward, or one local to the ActionMapping.
665      *
666      * @param definitionName the name of a Tiles definition, as defined
667      * in the Tiles configuration file.
668      *
669      * @exception AssertionFailedError if the ActionServlet controller
670      * used a different forward or tiles definition than those given after
671      * executing an Action object.
672      */
673     public void verifyTilesForward(String forwardName, String definitionName) {
674         if (logger.isTraceEnabled())
675             logger.trace("Entering - forwardName=" + forwardName + ", definitionName=" + definitionName);
676         init();
677         Common.verifyTilesForward(request.getPathInfo(),forwardName,definitionName,false,request,config.getServletContext(),config);
678         if (logger.isTraceEnabled())
679             logger.trace("Exiting");
680     }
681 
682     /**
683      * Verifies that the ActionServlet controller forwarded to the defined
684      * input Tiles definition.
685      *
686      * @param definitionName the name of a Tiles definition, as defined
687      * in the Tiles configuration file.
688      *
689      * @exception AssertionFailedError if the ActionServlet controller
690      * used a different forward than the defined input path after
691      * executing an Action object.
692      */
693     public void verifyInputTilesForward(String definitionName) {
694         if (logger.isTraceEnabled())
695             logger.trace("Entering - defintionName=" + definitionName);
696         init();
697         Common.verifyTilesForward(request.getPathInfo(),null,definitionName,true,request,config.getServletContext(),config);
698         if (logger.isTraceEnabled())
699             logger.trace("Exiting");
700     }
701 
702     /**
703      * Verifies if the ActionServlet controller sent these error messages.
704      * There must be an exact match between the provided error messages, and
705      * those sent by the controller, in both name and number.
706      *
707      * @param errorNames a String array containing the error message keys
708      * to be verified, as defined in the application resource properties
709      * file.
710      *
711      * @exception AssertionFailedError if the ActionServlet controller
712      * sent different error messages than those in <code>errorNames</code>
713      * after executing an Action object.
714      */
715 
716     public void verifyActionErrors(String[] errorNames) {
717         if (logger.isDebugEnabled())
718             logger.debug("Entering - errorNames = " + errorNames);
719         init();
720         Common.verifyActionMessages(request,errorNames,Globals.ERROR_KEY,"error");
721         if (logger.isDebugEnabled())
722             logger.debug("Exiting");
723     }
724 
725     /**
726      * Verifies that the ActionServlet controller sent no error messages upon
727      * executing an Action object.
728      *
729      * @exception AssertionFailedError if the ActionServlet controller
730      * sent any error messages after excecuting and Action object.
731      */
732     public void verifyNoActionErrors() {
733         if (logger.isDebugEnabled())
734             logger.debug("Entering");
735         init();
736         Common.verifyNoActionMessages(request,Globals.ERROR_KEY,"error");
737         if (logger.isDebugEnabled())
738             logger.debug("Exiting");
739     }
740 
741     /**
742      * Verifies if the ActionServlet controller sent these action messages.
743      * There must be an exact match between the provided action messages, and
744      * those sent by the controller, in both name and number.
745      *
746      * @param messageNames a String array containing the action message keys
747      * to be verified, as defined in the application resource properties
748      * file.
749      *
750      * @exception AssertionFailedError if the ActionServlet controller
751      * sent different action messages than those in <code>messageNames</code>
752      * after executing an Action object.
753      */
754     public void verifyActionMessages(String[] messageNames) {
755         if (logger.isDebugEnabled())
756             logger.debug("Entering - messageNames = " + messageNames);
757         init();
758         Common.verifyActionMessages(request,messageNames,Globals.MESSAGE_KEY,"action");
759         if (logger.isDebugEnabled())
760             logger.debug("Exiting");
761     }
762 
763     /**
764      * Verifies that the ActionServlet controller sent no action messages upon
765      * executing an Action object.
766      *
767      * @exception AssertionFailedError if the ActionServlet controller
768      * sent any action messages after excecuting and Action object.
769      */
770     public void verifyNoActionMessages() {
771         if (logger.isDebugEnabled())
772             logger.debug("Entering");
773         init();
774         Common.verifyNoActionMessages(request,Globals.MESSAGE_KEY,"action");
775         if (logger.isDebugEnabled())
776             logger.debug("Exiting");
777     }
778 
779     /**
780      * Returns the ActionForm instance stored in either the request or session.  Note
781      * that no form will be returned if the Action being tested cleans up the form
782      * instance.
783      *
784      * @ return the ActionForm instance used in this test, or null if it does not exist.
785      */
786     public ActionForm getActionForm() {
787         if (logger.isDebugEnabled())
788             logger.debug("Entering");
789         init();
790         if (logger.isDebugEnabled())
791             logger.debug("Exiting");
792         return Common.getActionForm(request.getPathInfo(),request,config.getServletContext());
793     }
794 
795     /**
796      * Sets an ActionForm instance to be used in this test.  The given ActionForm instance
797      * will be stored in the scope specified in the Struts configuration file (ie: request
798      * or session).  Note that while this ActionForm instance is passed to the test, Struts
799      * will still control how it is used.  In particular, it will call the ActionForm.reset()
800      * method, so if you override this method in your ActionForm subclass, you could potentially
801      * reset attributes in the form passed through this method.
802      *
803      * @param form the ActionForm instance to be used in this test.
804      */
805     public void setActionForm(ActionForm form) {
806         if (logger.isDebugEnabled())
807             logger.debug("Entering - form = " + form);
808         init();
809         // make sure ActionServlet is initialized.
810         Common.setActionForm(form,request,request.getPathInfo(),config.getServletContext());
811         if (logger.isDebugEnabled())
812             logger.debug("Exiting");
813     }
814 
815     /**
816      * Instructs StrutsTestCase to fully process a forward request. By default, StrutsTestCase
817      * stops processing a request as soon as the forward path has been collected, in order to avoid
818      * side effects; calling this method overrides this behavior.
819      * @param flag set to true to fully process forward requests
820      */
821     public void processRequest(boolean flag) {
822         if (logger.isTraceEnabled())
823             logger.trace("Entering - flag=" + flag);
824         ((StrutsServletContextWrapper) this.config.getServletContext()).setProcessRequest(flag);
825         if (logger.isTraceEnabled())
826             logger.trace("Exiting");
827     }
828 
829 }
830