Archive for January, 2008

Using Interceptors in Struts2

Thursday, January 24th, 2008

Interceptors are classes which implement com.opensymphony.xwork2.interceptor.Interceptor interface. Interceptors are configured in struts.xml. Interceptors are used for pre-processing and post-processing on Action invocations. Multiple interceptors can be applied to an action request.

Interceptor stack is a group of interceptors which can be referenced together. So instead of configuring a number of interceptors every time, we can just configure an interceptor stack with all the required interceptors in it.
Struts2 configures a default interceptor stack which handles all the generic functionalities required by action classes. These include Exception Interceptor, Validation Interceptor etc.

To demonstrate the use of interceptors, let us build an interceptor named “actiontimer” which will print the time required by an action request in milliseconds on the console. To ensure that time taken by default interceptors are not included, we will configure actiontimer as the last interceptor after default interceptor stack.

ActionTimer.java

struts.xml

interceptordemo.jsp

Struts2 Control Tags - Using iterator Tag

Wednesday, January 23rd, 2008

Download Source | View Demo

iterator tag can be used to loop over a collection of objects. The only requirement is that the collection should be of type java.util.Collection or java.util.iterator.

Here is a sample use,

Inside the iterator, the top of the value stack is the current object in the loop. Hence when you access “name”, it is actually “current_list_object.name”.

The current object is pushed to the value stack using the “id” field as the key. Hence referring “#userobj.name” is same as “name”. Similarly status field value (in this case user_stat) is the key in which the iterator status object is pushed. Hence you can check for an even row using the expression #user_stat.even which returns a boolean value.

Check out the following sample which demonstrates the use of iterator tag. In this IterateDemo action class populates dummy customer data is a list and passes it to iteratedemo.jsp. Using Struts2 iterator, the customer listing is printed out. Note the use of iterator status for alternate coloring of the rows. This sample also shows the use of stylesheets.

IterateDemo.java

Customer.java

iteratedemo.jsp

struts.xml

Parameters for iterator tag

Name Required Default Evaluated Type Description
id false false String Value stack key in which the current object is pushed
value false false String The list being iterated
status false false false String Value stack key in which the iterator status is stored

Form Validation in Struts2 - Basic Server Side Validation Example

Wednesday, January 23rd, 2008

Download Source | View Demo

One of the core Struts2 features is its comprehensive built in validation support. Struts2 supports a wide range of validation rules including regular expression validation. Data type validations supported are - conversion,date,double, email, expression, fieldexpression, int, regex, required, requiredstring,stringlength, url and visitor.

To use any of the predefined validators, no initial configuration is needed. Validation is implemented using a ValidationInterceptor which is configured in the default interceptor stack.

Struts2 supports serverside and client side validations. It also supports Ajax validation. Validations can be applied to specific form fields or it can be non field validations. It is also possible to create custom validators for any project specific validation requirements.

In this post, I will look at how simple server side validation can be implemented in Struts2.

We have a requirement to implement a screen which captures customer information. For simplicity, let us assume that this screen fields require the following validation.

Name : String with a maximum length of 50 characters
Age : Integer between 1 and 120
Email : A valid email address

The sample screen is given below.

sample-validation-screen1.jpg

First we need an action class to display the new customer form.

CustomerNewAction.java - Action class to dispatch to customer data capture form

customer_new.jsp - Form to capture customer data

One important thing to note here is the use of s:head tag. This injects the required stylesheets for error display after validation. The default theme used here is xhtml.

As you can see the input form is submitted to CustomerSaveAction. This will save the data and will dispatch to a page customer_save_success.jsp.

CustomerSaveAction.java - This is responsible for saving customer data. In this example, actual save is not implemented.

customer_save_success.jsp

Now we need to apply the declarative validation to CustomerSaveAction. To do that create a file CustomerSaveAction-validation.xml in the same folder which contains CustomerSaveAction.java. In Struts2, validation rules for an action class X is saved in a file X-validation.xml.

CustomerSaveAction-validation.xml

For more details on each of the validators and their parameters, please see here.

Let us connect everything together using struts.xml. Note the extra result tag (input) for CustomerSaveAction. It indicates the page to be displayed in case of input error.

struts.xml

web.xml

To invoke this sample, access the URL http://localhost:8080/struts2/CustomerNewAction.action. This is how the screen appears after validation,

sample-validation-screen2.jpg

Struts2 Control Tags – Using if Tag

Tuesday, January 22nd, 2008

Struts2 if tag can be used for basic conditional flow. Using OGNL syntax, all types of conditional checks are possible. This tag can be followed with elseif and else blocks. Given below are some examples of if tag usage.

Sample application demonstrating usage of Struts2 if tag
This sample contains a single page with a link. Whenever user clicks on the link, the clicked link name is shown below.

When a link is clicked, its id is copied to the linkid hidden field using JavaScript and IfDemo action is invoked. Struts2 automatically maps this hidden field to linkid field in IfDemo action class. Then it renders the ifdemo.jsp. At this point, class variables in IfDemo action class are automatically available in ifdemo.jsp (since they are pushed to value stack). The if tag in JSP checks for the value of linkid in value stack and prints it out.

Action Class - IfDemo.java

Struts configuration - struts.xml

Sample screen - ifdemo.jsp

Parameters for if tag

Name Required Default Evaluated Type Description
test true false boolean content inside the tag is displayed only if this boolean expression is true

Ajax file upload in Struts2 - Using Ajax File Upload Plugin

Saturday, January 19th, 2008

Download Source | View Demo

One of the advanced features of Struts2 is its plugin support. By using a standard interface API, you can seamlessly extend Struts2 capability.

Plugins are packaged as jar files along with any dependency jars. To use a plugin, you need to add it to the classpath. Struts automatically configures a plugin by using struts-plugin.xml packaged as part of the plugin jar.

When you use external plugins (plugins which are not part of standard Struts2 distribution) you must be aware of the risks. The plugin may not be fully tested and there could be other hidden issues. So always evaluate an external plugin before using it in a production server.

In this post, I will look at a very useful external Struts2 plugin - Monitored Ajax File Upload. Here is are the steps required for a sample demo.

yui-and-struts2-ajax-upload-plugin.jpg

1. Download Ajax File Upload plugin - You can download this from here.

2. Extract the zip and then copy the jars to WEB-INF/lib of your Web application. The jars are json-lib-2.0, commons-io-1.3.1, commons-fileupload-1.2 and AjaxFileUpload-0.03

3. Now create a FileUploadDemoAction action class extending from com.davidjc.ajaxfileupload.action.FileUpload. This is given below.

4. Configure struts.xml with the action and along with an additional interceptor as given below.

5. Create a JSP which contains file upload control. You need to use the ajaxfileuploadform custom tag. In this example, this jsp is ajaxupload.jsp.

6. This added files are displayed below the upload control using Ajax. For this YUI component connect is used for the GET request. The request is made to FileUploadDetailsAction and the results are returned using uploadlist.jsp. This content is added to the div tag (with id “did”) in the main page. Note how the ajax call is done from show_list method. This method is given as doafter parameter which is a JavaScript function executed immediately after file upload.

The above code also illustrates usage OGNL expressions and the use of status attribute on iterator tag for handling even/odd rows.

7. Configure the server location of the uploaded temporary file by setting struts.multipart.saveDir property. This can be done in struts.properties or web.xml. In this sample, it is set to c:/temp (windows machine) in web.xml. Make sure that the directory exists on the filesystem. In this example I have also set the maximum upload file size to 1MB using struts.multipart.maxSize property.

Complete details of the uploaded file is available in the FileUploadDemoAction. The temporary file created during upload is deleted after sometime. So you can use the File object to save the content to a separate folder or to a database.

To test this sample, use the JSP URL directly : http://localhost:8080/struts2demo/ajaxupload.jsp

Important: Ensure that you have Log4J jar in your application server’s lib folder.Also I am aware that this example gives errors and is not properly showing progress bar. I am still investigating these problems.

Got any questions? Don’t hesitate to contact me. Greetings to Dave Casserly for this excellent plugin.