I'm trying to find a way to configure in struts.xml an error message for each type of exception that can be thrown by an Action class. In an action class I could accomplish something similar by catching an exception, calling addActionError(String), and rethrowing the exception (provided an <exception-mapping> exists). Is there a way to do this through configuration?
As a reference point, this functionality exists in Struts1 with the key attribute on an exception handler - I'm hoping to be able to do something similar.
<exception key="some.key"
type="java.io.IOException"
handler="com.yourcorp.ExceptionHandler"/>
In strut2 also you can define exception mappings. Refer http://struts.apache.org/release/2.1.x/docs/exception-configuration.html. You can have a common error.jsp which displays a message that is looked up based on the class name of the exception.
In Struts2 you can use the following mapping to pass on the key/message to result (result can be a jsp or another action class).
<global-exception-mappings>
<exception-mapping exception="com.test.exception.MyCustomException" result="error">
<param name="param">display.custom.error</param>
</exception-mapping>
</global-exception-mappings>
<global-results>
<result name="error" type="chain">handleAction</result>
</global-results>
<action name="handleAction" class="HandleExceptionAction">
<result name="result">/WEB-INF/jsp/error.jsp</result>
</action>
If it an action class, in case of chaining (if the user wants to process the exception) then you need to have a corresponding attribute in Action class with getters and setters.
public class HandleExceptionAction extends ActionSupport implements
ServletRequestAware, SessionAware {
private **String param**;
private HttpServletRequest httpRequest;
private static final Log LOG = LogFactory.getLog(InputAction.class);
public String execute(){
LOG.debug("inside excute().....");
LOG.debug("Parameter passed:" + param);
System.out.println("Parameter passed:" + param);
return "result";
}
I am using spring injection, hope it will hep you.
Related
I have a program in which business logic return some data. that data needs to show on the jsp. i am able to forward to the jsp based on the result but how can i send the return value.
e.g.
public String createuser(String strUser,String strPassword)
{
String strReturnValue="S0000";
try
{
// My code;
}
catch(Exception ex)
{
}
return strReturnValue+"Token";
}
Struts.xml
<action name="RegUser" class="....">
<result name="success">/UIShow.jsp</result>
<result name="error>/UIError.jsp</result>
</action>
in jsp i want to show this token value on success; How can I do this?
You may want to check out the Hello World Struts 2 application because it provides a good example of how to do this.
In your Action class, you can create a String field and appropriate getter method for the token value so that your JSP can retrieve it. In your RegUser action method you will want to assign the field to the result from the business logic, like tokenValue = createUser(user, password);
In your UIShow.jsp you can use a struts 2 tag s:property to display the token value, like <s:property value="tokenValue"/>
Or, since this is just a String, it may be simpler for you to use the addActionMessage method from ActionSupport in your Action class (pass in the String result of the business logic into addActionMessage) and then use the s:actionmessage tag in your JSP to display the token value.
I have a question with respect to interceptors in Struts2
Struts2 provides very powerful mechanism of controlling a request using Interceptors. Interceptors are responsible for most of the request processing. They are invoked by the controller before and after invoking action, thus they sits between the controller and action. Interceptors performs tasks such as Logging, Validation, File Upload, Double-submit guard etc.
I have taken this above lines from:
http://viralpatel.net/blogs/2009/12/struts2-interceptors-tutorial-with-example.html
In this example you will see how the interceptors are invoked both before and after the execution of the action and how the results are rendered back to the user.
I have taken this above lines from
http://www.vaannila.com/struts-2/struts-2-example/struts-2-interceptors-example-1.html
I have written a basic interceptor and plugged it to my Action class:
public class InterceptorAction implements Interceptor {
public String intercept(ActionInvocation invocation) throws Exception {
System.out.println("Action class has been called : ");
return success;
}
}
struts.xml
<action name="login" class="com.DBAction">
<interceptor-ref name="mine"></interceptor-ref>
<result name="success">Welcome.jsp</result>
<result name="error">Login.jsp</result>
</action>
As per the above statements from their sites , i assumed that this line Action class has been called would be two times on the console (That is before the Action and after the Action class ) , but it has been printed only once?
PLease let me know , if my understanding is wrong , or the authors were wrong in that site ??
Not taking the time to read the page lets clear a few things up...
You are missing an important step in your interceptor.
Struts2, uses an object called ActionInvocation to manage calling the interceptors.
Lets give ActionInvocation a name (invocation) and show how the framework starts the ball rolling:
ActionInvocation invocation;
invocation.invoke(); //this is what the framework does... this method then calls the first interceptor in the chain.
Now we know interceptors can do pre-processing and post-processing... but the interface only defines one method to do the work of the interceptor (init and delete are just life cycle)! If the interface defined a doBefore and doAfter it would be easy so there must be some magic, happening...
As it turns out you are responsible for giving control back to action invocation at some point in your interceptor. This is a requirement. If you don't give control back to the ActionInvocation you will break the chain.
So when creating an interceptor you do the following steps
Create a class which implements com.opensymphony.xwork2.interceptor.Interceptor
[optional] do pre-processing work
call ActionInvocations invoke method to carry on processing down the stack and capture the return value.
[optional] do post processing as the above call unwinds.
return the string from step 3 (the result string) unless you have reason to do otherwise.
And here is a complete but pretty useless example:
package com.quaternion.interceptors;
import com.opensymphony.xwork2.ActionInvocation;
import com.opensymphony.xwork2.interceptor.Interceptor;
public class MyInterceptor implements Interceptor{
#Override
public void destroy() {
//nothing to do
}
#Override
public void init() {
//nothing to do
}
#Override
public String intercept(ActionInvocation invocation) throws Exception {
System.out.println("Something to do before the action!");
String resultString = invocation.invoke();
System.out.println("Something to do after the action!");
return resultString;
//if you are not doing post processing it is easiest to write
//return invocation.invoke();
}
}
struts.xml
<action name="tohome" class="action.ToSmsAction" method="execute">
<result name="success">/pages/home.jsp</result>
<result name="login">/pages/login.jsp</result>
</action>
TosmsAction.java
public class ToSmsAction extends ActionSupport {
private String time;
public String execute() {
System.out.println(" time is " + getTime());
return SUCCESS;
} else {
return LOGIN;
}
}
public String getTime() {
return time;
}
public void setTime(String time) {
this.time = time;
}
}
if i am not including class="action.ToSmsAction" then it is working good
but when including class="action.ToSmsAction" it is showing following error
HTTP Status 500 -
type Exception report
message
descriptionThe server encountered an internal error () that prevented it from fulfilling
this request.
exception
org.apache.jasper.JasperException: The Struts dispatcher cannot be found. This is
usually caused by using Struts tags without the associated filter. Struts tags are only
usable when the request has passed through its servlet filter, which initializes the
Struts dispatcher needed for this tag. - [unknown location]
root cause
The Struts dispatcher cannot be found. This is usually caused by using Struts tags
without the associated filter. Struts tags are only usable when the request has passed
through its servlet filter, which initializes the Struts dispatcher needed for this tag. -
[unknown location]
note The full stack traces of the exception and its root causes are available in the
GlassFish Server Open Source Edition 3.1.1 logs.
I got an interceptor that I'm trying to get to output a stream when a certain action is calling. This is part of my code in the inteceptor:
InputStream inputStream;
public String intercept(ActionInvocation invocation) throws Exception
{
if (currAction.contentEquals("actionToTest"))
{
String result = "TRUE";
inputStream = new ByteArrayInputStream(result.getBytes("UTF-8"));
return "resultToGiveStream";
}
}
inputStream has got it's own getters and setters.
And in struts.xml:
<global-results>
<result type="stream" name="resultToGiveStream">
<param name="contentType">text/plain</param>
<param name="inputName">inputStream</param>
</result>
</global-results>
But when I call actionToTest I only receive this in my console:
2011-maj-18 11:19:16 com.opensymphony.xwork2.util.logging.commons.CommonsLogger error
ALLVARLIG: Can not find a java.io.InputStream with the name [inputStream] in the invocation stack. Check the <param name="inputName"> tag specified for this action.
Is it a lost cause to get it to output what I want? I haven' found anyone doing anything similar.
This code is an atempt for a workaround for my other question.
Struts2 is looking for the getInputStream() method on your action and it isn't finding it.
You could try placing the inputStream on the stack manually from within the interceptor. Something like:
invocation.getInvocationContext().put("inputStream", inputStream);
I need to override the default conversion messages
So, I m trying to make a custom conversion error interceptor for my application which would be called instead of struts default interceptor
Below mentioned is the code for that
public class MyConversionErrorInterceptor extends ConversionErrorInterceptor {
private static final long serialVersionUID = 1L;
protected Object getOverrideExpr(ActionInvocation invocation, Object value) {
ValueStack stack = invocation.getStack();
return (String)stack.findValue("myproj.item");
}
protected boolean shouldAddError(String propertyName, Object value) {
return true;
}}
Here is the struts.xml configuration mentioned.
<interceptors >
<interceptor name="conversionError" class="com.celtic.cmvs.webapp.interceptor.MyConversionErrorInterceptor" />
<interceptor-stack name="myDefaultStack">
<interceptor-ref name="conversionError" />
<interceptor-ref name="defaultStack"/>
</interceptor-stack>
But it doesn't work.
Thanks in advance
I see a few possibilities.
The struts2 conversionError interceptor is still going to be called. If you want yours instead of the standard one, you need to define the entire stack yourself, with your interceptor in place of the standard one.
You might want to change the configured name of the custom interceptor so that it is not the same as the standard one. Otherwise, interceptor-ref name="conversionError" may still be pointing to the standard interceptor.
You need to make sure that your new stack is used. You can do that either by declaring it as the default stack, or by referencing the custom stack inside a specific action.
I have a tutorial on custom interceptors in my blog that may be useful: http://ddubbya.blogspot.com/2011/01/creating-custom-struts2-interceptors.html