Professional Documents
Culture Documents
Many Actions share common concerns. Some Actions need input validated. Other
Actions may need a file upload to be pre-processed. Another Action might need
protection from a double submit. Many Actions need drop-down lists and other controls
pre-populated before the page displays.
The framework makes it easy to share solutions to these concerns using an "Interceptor"
strategy. When you request a resource that maps to an "action", the framework invokes
the Action object. But, before the Action is executed, the invocation can be intercepted
by another object. After the Action executes, the invocation could be intercepted again.
Unsurprisingly, we call these objects "Interceptors."
Understanding Interceptors
Interceptors can execute code before and after an Action is invoked. Most of the
framework's core functionality is implemented as Interceptors. Features like double-
submit guards, type conversion, object population, validation, file upload, page
preparation, and more, are all implemented with the help of Interceptors. Each and every
Interceptor is pluggable, so you can decide exactly which features an Action needs to
support.
Interceptors can be configured on a per-action basis. Your own custom Interceptors can
be mixed-and-matched with the Interceptors bundled with the framework. Interceptors
"set the stage" for the Action classes, doing much of the "heavy lifting" before the Action
executes.
Action Lifecyle
In some cases, an Interceptor might keep an Action from firing, because of a double-
submit or because validation failed. Interceptors can also change the state of an Action
before it executes.
The Interceptors are defined in a stack that specifies the execution order. In some cases,
the order of the Interceptors on the stack can be very important.
Configuring Interceptors
struts.xml
<package name="default" extends="struts-default">
<interceptors>
<interceptor name="timer" class=".."/>
<interceptor name="logger" class=".."/>
</interceptors>
<action name="login"
class="tutorial.Login">
<interceptor-ref name="timer"/>
<interceptor-ref name="logger"/>
<result name="input">login.jsp</result>
<result name="success"
type="redirect-action">/secure/home</result>
</action>
</package>
Stacking Interceptors
With most web applications, we find ourselves wanting to apply the same set of
Interceptors over and over again. Rather than reiterate the same list of Interceptors, we
can bundle these Interceptors together using an Interceptor Stack.
struts.xml
<package name="default" extends="struts-default">
<interceptors>
<interceptor name="timer" class=".."/>
<interceptor name="logger" class=".."/>
<interceptor-stack name="myStack">
<interceptor-ref name="timer"/>
<interceptor-ref name="logger"/>
</interceptor-stack>
</interceptors>
<action name="login"
class="tutuorial.Login">
<interceptor-ref name="myStack"/>
<result name="input">login.jsp</result>
<result name="success"
type="redirect-action">/secure/home</result>
</action>
</package>
<struts>
<bean class="com.opensymphony.xwork2.ObjectFactory" name="xwork" />
<bean type="com.opensymphony.xwork2.ObjectFactory" name="struts"
class="org.apache.struts2.impl.StrutsObjectFactory" />
<bean type="com.opensymphony.xwork2.util.ObjectTypeDeterminer"
name="tiger"
class="com.opensymphony.xwork2.util.GenericsObjectTypeDeterminer"/>
<bean type="com.opensymphony.xwork2.util.ObjectTypeDeterminer"
name="notiger"
class="com.opensymphony.xwork2.util.DefaultObjectTypeDeterminer"/>
<bean type="com.opensymphony.xwork2.util.ObjectTypeDeterminer"
name="struts"
class="com.opensymphony.xwork2.util.DefaultObjectTypeDeterminer"/>
<bean type="org.apache.struts2.dispatcher.mapper.ActionMapper"
name="struts"
class="org.apache.struts2.dispatcher.mapper.DefaultActionMapper" />
<bean type="org.apache.struts2.dispatcher.mapper.ActionMapper"
name="composite"
class="org.apache.struts2.dispatcher.mapper.CompositeActionMapper" />
<bean type="org.apache.struts2.dispatcher.mapper.ActionMapper"
name="restful"
class="org.apache.struts2.dispatcher.mapper.RestfulActionMapper" />
<bean type="org.apache.struts2.dispatcher.mapper.ActionMapper"
name="restful2"
class="org.apache.struts2.dispatcher.mapper.Restful2ActionMapper" />
<bean
type="org.apache.struts2.dispatcher.multipart.MultiPartRequest"
name="struts"
class="org.apache.struts2.dispatcher.multipart.JakartaMultiPartRequest"
scope="default" optional="true"/>
<bean
type="org.apache.struts2.dispatcher.multipart.MultiPartRequest"
name="jakarta"
class="org.apache.struts2.dispatcher.multipart.JakartaMultiPartRequest"
scope="default" optional="true" />
<bean class="org.apache.struts2.views.freemarker.FreemarkerManager"
name="struts" optional="true"/>
<bean class="org.apache.struts2.views.velocity.VelocityManager"
name="struts" optional="true" />
<bean
class="org.apache.struts2.components.template.TemplateEngineManager" />
<bean type="org.apache.struts2.components.template.TemplateEngine"
name="ftl"
class="org.apache.struts2.components.template.FreemarkerTemplateEngine"
/>
<bean type="org.apache.struts2.components.template.TemplateEngine"
name="vm"
class="org.apache.struts2.components.template.VelocityTemplateEngine" />
<bean type="org.apache.struts2.components.template.TemplateEngine"
name="jsp"
class="org.apache.struts2.components.template.JspTemplateEngine" />
<bean type="com.opensymphony.xwork2.util.XWorkConverter"
name="xwork1" class="com.opensymphony.xwork2.util.XWorkConverter" />
<bean type="com.opensymphony.xwork2.util.XWorkConverter"
name="struts"
class="com.opensymphony.xwork2.util.AnnotationXWorkConverter" />
<bean type="org.apache.struts2.components.UrlRenderer"
name="struts" class="org.apache.struts2.components.ServletUrlRenderer"/>
<interceptors>
<interceptor name="alias"
class="com.opensymphony.xwork2.interceptor.AliasInterceptor"/>
<interceptor name="autowiring"
class="com.opensymphony.xwork2.spring.interceptor.ActionAutowiringInter
ceptor"/>
<interceptor name="chain"
class="com.opensymphony.xwork2.interceptor.ChainingInterceptor"/>
<interceptor name="conversionError"
class="org.apache.struts2.interceptor.StrutsConversionErrorInterceptor"
/>
<interceptor name="createSession"
class="org.apache.struts2.interceptor.CreateSessionInterceptor" />
<interceptor name="debugging"
class="org.apache.struts2.interceptor.debugging.DebuggingInterceptor" />
<interceptor name="externalRef"
class="com.opensymphony.xwork2.interceptor.ExternalReferencesIntercepto
r"/>
<interceptor name="execAndWait"
class="org.apache.struts2.interceptor.ExecuteAndWaitInterceptor"/>
<interceptor name="exception"
class="com.opensymphony.xwork2.interceptor.ExceptionMappingInterceptor"
/>
<interceptor name="fileUpload"
class="org.apache.struts2.interceptor.FileUploadInterceptor"/>
<interceptor name="i18n"
class="com.opensymphony.xwork2.interceptor.I18nInterceptor"/>
<interceptor name="logger"
class="com.opensymphony.xwork2.interceptor.LoggingInterceptor"/>
<interceptor name="modelDriven"
class="com.opensymphony.xwork2.interceptor.ModelDrivenInterceptor"/>
<interceptor name="scopedModelDriven"
class="com.opensymphony.xwork2.interceptor.ScopedModelDrivenInterceptor"
/>
<interceptor name="params"
class="com.opensymphony.xwork2.interceptor.ParametersInterceptor"/>
<interceptor name="prepare"
class="com.opensymphony.xwork2.interceptor.PrepareInterceptor"/>
<interceptor name="staticParams"
class="com.opensymphony.xwork2.interceptor.StaticParametersInterceptor"
/>
<interceptor name="scope"
class="org.apache.struts2.interceptor.ScopeInterceptor"/>
<interceptor name="servletConfig"
class="org.apache.struts2.interceptor.ServletConfigInterceptor"/>
<interceptor name="sessionAutowiring"
class="org.apache.struts2.spring.interceptor.SessionContextAutowiringIn
terceptor"/>
<interceptor name="timer"
class="com.opensymphony.xwork2.interceptor.TimerInterceptor"/>
<interceptor name="token"
class="org.apache.struts2.interceptor.TokenInterceptor"/>
<interceptor name="tokenSession"
class="org.apache.struts2.interceptor.TokenSessionStoreInterceptor"/>
<interceptor name="validation"
class="org.apache.struts2.interceptor.validation.AnnotationValidationIn
terceptor"/>
<interceptor name="workflow"
class="com.opensymphony.xwork2.interceptor.DefaultWorkflowInterceptor"/>
<interceptor name="store"
class="org.apache.struts2.interceptor.MessageStoreInterceptor" />
<interceptor name="checkbox"
class="org.apache.struts2.interceptor.CheckboxInterceptor" />
<interceptor name="profiling"
class="org.apache.struts2.interceptor.ProfilingActivationInterceptor" />
<interceptor name="roles"
class="org.apache.struts2.interceptor.RolesInterceptor" />
<interceptor name="jsonValidation"
class="org.apache.struts2.interceptor.validation.JSONValidationIntercep
tor" />
<interceptor name="annotationWorkflow"
class="com.opensymphony.xwork2.interceptor.annotations.AnnotationWorkfl
owInterceptor" />
</interceptors>
<default-interceptor-ref name="defaultStack"/>
</package>
</struts>
Framework Interceptors
Interceptor classes are also defined using a key-value pair specified in the Struts
configuration file. The names specified below come specified in struts-default.xml. If you
extend the struts-default package, then you can use the names below. Otherwise, they
must be defined in your package with a name-class pair specified in the <interceptors>
tag.
Method Filtering
• TokenInterceptor
• TokenSessionStoreInterceptor
• DefaultWorkflowInterceptor
• ValidationInterceptor
Method 2:
In the first method, the whole default stack is copied and the parameter then changed
accordingly.
tag, the name attribute contains a dot (.) the word before the dot(.) specifies the
interceptor name whose parameter is to be overriden and the word after the dot (.)
specifies the parameter itself. Essetially it is as follows :-
<interceptor-name>.<parameter-name>
Note also that in this case the name attribute is used to indicate an interceptor stack which
makes sense as if it is refering to the interceptor itself it would be just using Method 1
describe above.
<interceptor-stack name="xaStack">
<interceptor-ref name="thisWillRunFirstInterceptor"/>
<interceptor-ref name="thisWillRunNextInterceptor"/>
<interceptor-ref name="followedByThisInterceptor"/>
<interceptor-ref name="thisWillRunLastInterceptor"/>
</interceptor-stack>
Note that some Interceptors will interrupt the stack/chain/flow ... so the order is very
important.
Interceptors implementing
com.opensymphony.xwork2.interceptor.PreResultListener will run after the
Action executes but before the Result executes.
thisWillRunFirstInterceptor
thisWillRunNextInterceptor
followedByThisInterceptor
thisWillRunLastInterceptor
MyAction1
MyAction2 (chain)
MyPreResultListener
MyResult (result)
thisWillRunLastInterceptor
followedByThisInterceptor
thisWillRunNextInterceptor
thisWillRunFirstInterceptor
FAQ
• How do we configure an Interceptor to be used with every Action?
• How do we get access to the session?
• How can we access the HttpServletRequest?
• How can we access the HttpServletResponse?
• How can we access request parameters passed into an Action?
• How do we access static parameters from an Action?
• Can we access an Action's Result?
• How do I obtain security details (JAAS)?
• Why isn't our Prepare interceptor being executed?
• How do we upload files?
<interceptor-ref name="timer"/>
<interceptor-ref name="logger"/>
<interceptor-ref name="default-stack"/>
<result name="input">login.jsp</result>
<result type="redirect-action">/secure/home</result>
</action>
Or, we can create our own named stacks and even declare a new default interceptor stack
for a package
<default-interceptor-ref name="myStack"/>
</package>
Packages can extend other packages. If all the other packages in your application extend
"default", then they will all inherit the new default interceptor.
You can obtain the session attributes by asking the ActionContext or implementing
SessionAware. Implementing SessionAware is preferred.
Implement ServletRequestAware
Preferred
Implement ServletResponseAware
Preferred
You can obtain the request parameters by asking the ActionContext or implementing
ParameterAware. Implementing ParameterAware is preferred.
Implement ParameterAware
Preferred
Static (or pre-defined) parameters can be set to a Map property or to individual JavaBean
properties.
• Define the parameters to be set by adding the name(s) and value(s) to the action
mapping element (in the application's struts.xml.
Map property
• Ensure the Action defines a setParams(Map) method.
• The static-params Interceptor will set the defined values to the Map, using the
name as the entry key.
key value
myStaticParam1 myStaticValue1
myStaticParam2 myStaticValue2
myStaticParam3 myStaticValue3
JavaBean properties
• Ensure that the Action defines JavaBean properties corresponding to the param
elements in the action mapping.
Yes, you can access the ResultConfig objects before the Action executes, and you can
access the final Result object using a PreResultListener.
Accessing the ResultConfig Objects
If you need to work with the set of ResultConfigs before the Action executes, you can use
an Interceptor to process the Map returned by getResults.
return invocation.invoke();
}
// ...
}
If you are writing against Java 5, you could use a generic when obtain the map.
Adding a PreResultListener
If you need to work with the final Result object before it is executed, you can use an
Interceptor to register a PreResultListener. The code example creates a PreResultListener
as an anonymous inner class.
invocation.addPreResultListener(new PreResultListener() {
});
return invocation.invoke();
}
// ...
}
If you are writing against Java 5, you could use a generic when obtain the map.
You can obtain the UserPrincipal and other security details by going through the request
or implementing PrincipalAware. Implementing PrincipalAware is preferred.
Implement PrincipalAware
Preferred
Sometimes the order of the Interceptors makes a difference. In the case of the prepare
Interceptor, ensure that it comes before validation on the interceptor-stack.
<interceptor-stack name="myInterceptorStack">
...
<interceptor-ref name="prepare" />
...
<interceptor-ref name="validation" />
...
</interceptor-stack>
The default stack does place the prepare Interceptor before the
validation Inteceptor.
How do we upload files
Edit Page Browse Space Add Page Add News
Added by tm_jee, last edited by Ted Husted on Jan 28, 2007 (view change)
• Ensure that the Action provides one or more fileUpload mutator methods, with
names that correspond to name of the file type input.
When multiple files are uploaded by a form, the files are represented by an array.
Given:
The Action class can define file handling methods that accept an array.
The uploaded files can be handled by iterating through the appropriate array.
Extra Information
Property Default
struts.multipart.parser Commons FileUpload
struts.multipart.saveDir javax.servlet.context.tempdir as defined by container
struts.multipart.maxSize Approximately 2M
Writing Interceptors
Edit Page Browse Space Add Page Add News
Added by Musachy Barroso, last edited by Musachy Barroso on Jul 09, 2007 (view
change)
Interceptor interface
Interceptor.java
public interface Interceptor extends Serializable {
void destroy();
void init();
String intercept(ActionInvocation invocation) throws Exception;
}
The init method is called the after interceptor is instantiated and before calling intercept.
This is the place to allocate any resources used by the interceptor.
The intercept method is where the interceptor code is written. Just like an action method,
intercept returns a result used by Struts to forward the request to another web resource.
Calling invoke on the parameter of type ActionInvocation will execute the action (if this
is the last interceptor on the stack) or another interceptor.
Keep in mind that invoke will return after the result has been called (eg.
after you JSP has been rendered), making it perfect for things like open-
session-in-view patterns. If you want to do something before the result
gets called, you should implement a PreResultListener.
Thread Safety
A Struts 2 Action instance is created for every request and do not need
to be thread-safe. Conversely, Interceptors are shared between requests
and must be thread-safe .
AbstractInterceptor
The AbstractInterceptor class provides an empty implementation of init and destroy, and
can be used if these methods are not going to be implemented.
Mapping
Interceptors are declared using the interceptor element, nested inside the interceptors
element. Example from struts-default.xml:
<struts>
...
<package name="struts-default">
<interceptors>
<interceptor name="alias"
class="com.opensymphony.xwork2.interceptor.AliasInterceptor"/>
<interceptor name="autowiring"
class="com.opensymphony.xwork2.spring.interceptor.ActionAutowiringInter
ceptor"/>
...
</interceptors>
</package>
...
</struts>
Example
Interceptor Example
import com.opensymphony.xwork2.ActionInvocation;
import com.opensymphony.xwork2.interceptor.AbstractInterceptor;
The framework provides the ability to chain multiple actions into a defined sequence or
workflow. This feature works by applying a Chain Result to a given Action, and
intercepting its target Action's invocation with a ChainingInterceptor .
Chain Result
The Chain Result is a result type that invokes an Action with its own Interceptor Stack
and Result. This Interceptor allows an Action to forward requests to a target Action,
while propagating the state of the source Action. Below is an example of how to define
this sequence.
Another action mapping in the same namespace (or the default "" namespace) can be
executed after this action mapping (see Configuration Files). An optional "namespace"
parameter may also be added to specify an action in a different namespace.
Chaining Interceptor
If you need to copy the properties from your previous Actions in the chain to the current
action, you should apply the ChainingInterceptor . The Interceptor will copy the original
parameters from the request, and the ValueStack is passed in to the target Action. The
source Action is remembered by the ValueStack, allowing the target Action to access the
properties of the preceding Action(s) using the ValueStack, and also makes these
properties available to the final result of the chain, such as the JSP or Velocity page.
One common use of Action chaining is to provide lookup lists (like for a dropdown list of
states). Since these Actions get put on the ValueStack, their properties will be available in
the view. This functionality can also be done using the ActionTag to execute an Action
from the display page. You may also use the Redirect Action Result to accomplish this.
Result Types
Edit Page Browse Space Add Page Add News
Added by casey, last edited by Philip Luppens on Mar 13, 2007 (view change) show
comment
Most use cases can be divided into two phases. First, we need to change or query the
application's state, and then we need to present an updated view of the application. The
Action class manages the application's state, and the Result Type manages the view.
Optional
Additional Result Types can be created and plugged into an application by implementing
the com.opensymphony.xwork2.Result interface. Custom Result Types might include
generating an email or JMS message, generating images, and so forth.
Chain Result
Edit Page Browse Space Add Page Add News
Added by casey, last edited by Philip Luppens on Feb 10, 2007 (view change) show
comment
This result invokes an entire other action, complete with it's own interceptor stack and
result.
Parameters
• actionName (default) - the name of the action that will be chained to
• namespace - used to determine which namespace the Action is in that we're
chaining. If namespace is null, this defaults to the current namespace
• method - used to specify another method on target action to be invoked. If null,
this defaults to execute method
• skipActions - (optional) the list of comma separated action names for the actions
that could be chained to
Examples
<package name="public" extends="struts-default">
<!-- Chain creatAccount to login, using the default parameter -->
<action name="createAccount" class="...">
<result type="chain">login</result>
</action>
Includes or forwards to a view (usually a jsp). Behind the scenes Struts will use a
RequestDispatcher, where the target servlet/JSP receives the same request/response
objects as the original servlet/JSP. Therefore, you can pass data between them using
request.setAttribute() - the Struts action is available.
Parameters
• location (default) - the location to go to after execution (ex. jsp).
• parse - true by default. If set to false, the location param will not be parsed for
Ognl expressions.
Examples
<result name="success" type="dispatcher">
<param name="location">foo.jsp</param>
</result>
FreeMarker Result
Edit Page Browse Space Add Page Add News
Added by casey, last edited by Ted Husted on Sep 10, 2006 (view change)
The FreemarkarManager class configures the template loaders so that the template
location can be either
Parameters
• location (default) - the location of the template to process.
• parse - true by default. If set to false, the location param will not be parsed for
Ognl expressions.
• contentType - defaults to "text/html" unless specified.
• writeIfCompleted - false by default, write to stream only if there isn't any error
processing the template. Setting template_exception_handler=rethrow in
freemarker.properties will have the same effect.
Examples
<result name="success" type="freemarker">foo.ftl</result>
HttpHeader Result
Edit Page Browse Space Add Page Add News
Added by casey, last edited by Ted Husted on Sep 10, 2006 (view change)
A custom Result type for setting HTTP headers and status by optionally evaluating
against the ValueStack. This result can also be used to send and error to the client.
Parameters
• status - the http servlet response status code that should be set on a response.
• parse - true by default. If set to false, the headers param will not be parsed for
Ognl expressions.
• headers - header values.
• error - the http servlet response error code that should be set on a response.
• errorMessage - error message to be set on response if 'error' is set.
Examples
<result name="success" type="httpheader">
<param name="status">204</param>
<param name="headers.a">a custom header value</param>
<param name="headers.b">another custom header value</param>
</result>
Parameters
• location (default) - the location to go to after execution.
• parse - true by default. If set to false, the location param will not be parsed for
Ognl expressions.
Examples
<result name="success" type="redirect">
<param name="location">foo.jsp</param>
<param name="parse">false</param>
</result>
Redirect Action Result
Edit Page Browse Space Add Page Add News
Added by Patrick Lightbody, last edited by Ted Husted on Sep 04, 2006 (view change)
This result uses the ActionMapper provided by the ActionMapperFactory to redirect the
browser to a URL that invokes the specified action and (optional) namespace. This is
better than the ServletRedirectResult because it does not require you to encode the URL
patterns processed by the ActionMapper in to your struts.xml configuration files. This
means you can change your URL patterns at any point and your application will still
work. It is strongly recommended that if you are redirecting to another action, you use
this result rather than the standard redirect result.
See examples below for an example of how request parameters could be passed in.
Parameters
• actionName (default) - the name of the action that will be redirect to
• namespace - used to determine which namespace the action is in that we're
redirecting to . If namespace is null, this defaults to the current namespace
Examples
<package name="public" extends="struts-default">
<action name="login" class="...">
<!-- Redirect to another namespace -->
<result type="redirect-action">
<param name="actionName">dashboard</param>
<param name="namespace">/secure</param>
</result>
</action>
</package>
A custom Result type for send raw data (via an InputStream) directly to the
HttpServletResponse. Very useful for allowing users to download content.
If you are running your app server under HTTPS and having issues with
PDF's or other file streams you should take a look at HTTPS and IE
Issues
Parameters
• contentType - the stream mime-type as sent to the web browser (default =
text/plain).
• contentLength - the stream length in bytes (the browser displays a progress bar).
• contentDispostion - the content disposition header value for specifing the file
name (default = inline, values are typically filename="document.pdf".
• inputName - the name of the InputStream property from the chained action
(default = inputStream).
• bufferSize - the size of the buffer to copy from input to output (default = 1024).
Examples
<result name="success" type="stream">
<param name="contentType">image/jpeg</param>
<param name="inputName">imageStream</param>
<param name="contentDisposition">filename="document.pdf"</param>
<param name="bufferSize">1024</param>
</result>
Apache Struts 2 Documentation
Velocity Result
Edit Page Browse Space Add Page Add News
Added by casey, last edited by Ted Husted on Sep 10, 2006 (view change)
Using the Servlet container's JspFactory, this result mocks a JSP execution environment
and then displays a Velocity template that will be streamed directly to the servlet output.
Parameters
• location (default) - the location of the template to process.
• parse - true by default. If set to false, the location param will not be parsed for
Ognl expressions.
Examples
<result name="success" type="velocity">
<param name="location">foo.vm</param>
</result>
XSL Result
Edit Page Browse Space Add Page Add News
Added by casey, last edited by Ted Husted on Sep 10, 2006 (view change)
XSLTResult uses XSLT to transform an action object to XML. The recent version has
been specifically modified to deal with Xalan flaws. When using Xalan you may notice
that even though you have a very minimal stylesheet like this one
<xsl:template match="/result">
<result/>
</xsl:template>
Xalan would still iterate through every property of your action and all its descendants.
If you had double-linked objects, Xalan would work forever analysing an infinite object
tree. Even if your stylesheet was not constructed to process them all. It's because the
current Xalan eagerly and extensively converts everything to its internal DTM model
before further processing.
That's why there's a loop eliminator added that works by indexing every object-property
combination during processing. If it notices that some object's property was already
walked through, it doesn't go any deeper. Say you have two objects, x and y, with the
following properties set (pseudocode):
x.y = y;
and
y.x = x;
action.x=x;
Due to that modification, the resulting XML document based on x would be:
<result>
<x>
<y/>
</x>
</result>
Sometimes the object mesh is still very dense and you may notice that even though you
have a relatively simple stylesheet, execution takes a tremendous amount of time. To help
you to deal with that obstacle of Xalan, you may attach regexp filters to elements paths
(xpath).
Note: In your .xsl file the root match must be named result.
This example will output the username by using getUsername on your action class:
<xsl:template match="result">
<html>
<body>
Hello <xsl:value-of select="username"/> how are you?
</body>
</html>
<xsl:template/>
In the following example the XSLT result would only walk through action's properties
without their childs. It would also skip every property that has "hugeCollection" in their
name. Element's path is first compared to excludingPattern - if it matches it's no longer
processed. Then it is compared to matchingPattern and processed only if there's a match.
Parameters
• location (default) - the location to go to after execution.
• parse - true by default. If set to false, the location param will not be parsed for
Ognl expressions.
• matchingPattern - Pattern that matches only desired elements, by default it
matches everything.
• excludingPattern - Pattern that eliminates unwanted elements, by default it
matches none.
A result that send the content out as plain text. Usefull typically when needed to display
the raw content of a JSP or Html file for example.
Parameters
• location (default) = location of the file (jsp/html) to be displayed as plain text.
• charSet (optional) = character set to be used. This character set will be used to set
the response type (eg. Content-Type=text/plain; charset=UTF-8) and when
reading using a Reader. Some example of charSet would be UTF-8, ISO-8859-1
etc.
Examples
<action name="displayJspRawContent" >
<result type="plaintext">/myJspFile.jsp</result>
</action>
Example
static {
Dispatcher.addDispatcherListener(new DispatcherListener() {
public void dispatcherInitialized(Dispatcher du) {
// do something to Dispatcher after it is initialized eg.
du.setConfigurationManager(....);
}
Examples
A PreResultListener can be added by an Action or an Interceptor.
By an Action
public class MyAction extends ActionSupport {
...
public String execute() throws Exception {
ActionInvocation invocation =
ActionContext.getActionInvocation();
invocation.addPreResultListener(new PreResultListener() {
public void beforeResult(ActionInvocation invocation,
String resultCode) {
// perform operation necessary before Result execution
}
});
}
...
}
By an Interceptor
public class MyInterceptor extends AbstractInterceptor {
...
public String intercept(ActionInvocation invocation) throws
Exception {
invocation.addPreResultListener(new PreResultListener() {
public void beforeResult(ActionInvocation invocation,
String resultCode) {
// perform operation necessary before Result execution
}
});
}
...
}