Monday, November 06, 2006

Struts 2: Validation

Update: A new post for validation in struts with annotation is available at: Struts 2 Validation: Annotations.

Struts 2.0 relies on a validation framework provided by XWork input validation. Along with basic validation and client-side Javascript validation offered in Struts 1.x, Struts 2 offers Ajax based validation. The following example demonstrates how to use Struts 2 validation, both basic and ajax validations. For this, the sample page used is shown below.
<s:form action="RegisterUser">
<s:textfield name="userName" size="20" label="User Name" />
<s:textfield name="emailAddress" size="20" label="Email Address" />
<s:textfield name="dateOfBirth" size="20" label="Date Of Birth" />
<s:submit name="submit" value="submit" />
</s:form>
The Action definition is shown below:
<action name="RegisterUser" method="registerUser" class="example.RegisterUser">
<result name="input">/example/Register.jsp</result>
<result>/example/HelloWorld.jsp</result>
</action>
Based on above definition, the Action class must have a method name registerUser.
Basic Validation
For basic validaton, you have to define the validation rules in <ActionClassName>-validation.xml file. The validations for this form are defined in the RegisterUser-validation.xml file as follows
<validators>
<field name="userName">
<field-validator type="requiredstring">
<message key="requiredstring" />
</field-validator>
</field>
<field name="emailAddress">
<field-validator type="email">
<message key="fieldFormat" />
</field-validator>
</field>
<field name="dateOfBirth">
<field-validator type="requiredstring">
<message key="requiredstring" />
</field-validator>
<field-validator type="regex">
<param name="expression">
[0-9][0-9]/[0-9][0-9]/[1-9][0-9][0-9][0-9]
</param>
<message key="fieldFormat" />
</field-validator>
</field>
</validators>
Note that the "date of birth" field has two validators associated with it. The "regex" validator type takes a parameter by the name "expression" which is the regular expression used to validate the field. The message keys used in validation rules must be defined in "package.properties" file as follows:
requiredstring = ${getText(fieldName)} is required.
fieldFormat = ${getText(fieldName)} is not formatted properly.

Client Side Validation
For simple client-side validation without Ajax, just add a validate="true" to the form definition in the JSP, as follows:
<s:form action="RegisterUser" validate="true">
Also note that the message keys do not work(atleast not for me), and you may have to define the error messages directly instead of through the properties file as follows:
<message>Date of birth is not formatted properly</message>

Ajax Validation
Struts implements Ajax Validation by using DWR. For a quick start of DWR read Ajax in Java with DWR. Coming to Struts validation, follow these steps to setup DWR
  1. Download DWR from here.
  2. Add DWR servlet mapping in the web deployment descriptor as shown below
    <servlet>
    <servlet-name>dwr</servlet-name>
    <servlet-class>uk.ltd.getahead.dwr.DWRServlet</servlet-class>
    <init-param>
    <param-name>debug</param-name>
    <param-value>true</param-value>
    </init-param>
    </servlet>
    <servlet-mapping>
    <servlet-name>dwr</servlet-name>
    <url-pattern>/dwr/*</url-pattern>
    </servlet-mapping>
  3. In your WEB-INF directory, create a dwr.xml file and declare the struts validator as follows
    <!DOCTYPE dwr PUBLIC
    "-//GetAhead Limited//DTD Direct Web Remoting 1.0//EN"
    "http://www.getahead.ltd.uk/dwr/dwr10.dtd">

    <dwr>
    <allow>
    <create creator="new" javascript="validator">
    <param name="class"
    value="org.apache.struts2.validators.DWRValidator" />
    </create>
    <convert converter="bean"
    match="com.opensymphony.xwork2.ValidationAwareSupport" />
    </allow>

    <signatures>
    <![CDATA[
    import java.util.Map;
    import org.apache.struts2.validators.DWRValidator;

    DWRValidator.doPost(String, String, Map<String, String>);
    ]]>
    </signatures>
    </dwr>
  4. Change the form declaration in your JSP file to include "theme=ajax" as shown below
    <s:form action="RegisterUser" validate="true" theme="ajax">
This example was tested using Tomcat 5.5 on Java 1.5.

Friday, November 03, 2006

Using Sitemesh with Struts 2.0

SiteMesh is a web-page layout and decoration framework and web-application integration framework like Tiles that can be used to give a consistent look and feel to your site. While tiles, which works with templates, SiteMesh acts as a decorator around your HTML pages that go through the web-server. SiteMesh can also include entire HTML pages as a Panel within another page. Using this feature, Portal type web sites can be built very quickly and effectively. As one might expect, SiteMesh works with Servlet filters to achieve this. The following example demonstrates the use of SiteMesh with Struts 2.0. I am just going to use the struts-blank application and add SiteMesh decorator to the welcome page.

Setup SiteMesh
  1. Import struts-blank.war into Eclipse and rename it.
  2. Download the latest version of SiteMesh (v2.3) from here.
  3. Copy sitemesh-2.3.jar to the WEB-INF/lib folder of your web application.
  4. Add a filter mapping for sitemesh to web.xml file. As discussed in the previous post (Struts 2.0 controller), you need to add the ActionContextCleanup filter too. Your web.xml filter descriptions should look like this:

    <filter>
    <filter-name>struts-cleanup</filter-name>
    <filter-class>
    org.apache.struts2.dispatcher.ActionContextCleanUp
    </filter-class>
    </filter>
    <filter>
    <filter-name>sitemesh</filter-name>
    <filter-class>
    com.opensymphony.module.sitemesh.filter.PageFilter
    </filter-class>
    </filter>
    <filter>
    <filter-name>struts2</filter-name>
    <filter-class>
    org.apache.struts2.dispatcher.FilterDispatcher
    </filter-class>
    </filter>

    <filter-mapping>
    <filter-name>struts-cleanup</filter-name>
    <url-pattern>/*</url-pattern>
    </filter-mapping>
    <filter-mapping>
    <filter-name>sitemesh</filter-name>
    <url-pattern>/*</url-pattern>
    </filter-mapping>
    <filter-mapping>
    <filter-name>struts2</filter-name>
    <url-pattern>/*</url-pattern>
    </filter-mapping>

This completes the setup of your web application for using sitemesh.

Creating Decorators
Once your web application is setup for SiteMesh, you can start writing your decorators. For this, first create a decorators.xml file in your WEB-INF directory. For this example we will define a single decorator layout.jsp. The decorators.xml file is shown below
<?xml version="1.0" encoding="ISO-8859-1"?>
<decorators defaultdir="/decorators">
<decorator name="main" page="layout.jsp">
<pattern>/*</pattern>
</decorator>
<decorator name="panel" page="panel.jsp" />
</decorators>


Once we define the decorators in the decorators.xml file, we have to create the decorators themselves. The following is the code for layout.jsp
<%@ taglib uri="http://www.opensymphony.com/sitemesh/decorator"
prefix="decorator"%>
<%@ taglib uri="http://www.opensymphony.com/sitemesh/page"
prefix="pages"%>
<html>
<head>
<title>My Site - <decorator:title default="Welcome!" /></title>
<decorator:head />
</head>

<body>
<table>
<tr>
<td bgcolor="skyblue"><pages:applyDecorator page="/paneldata.html"
name="panel" title="Left Panel" /></td>
<td><decorator:body /></td>
<td bgcolor="gray"><pages:applyDecorator page="/paneldata.html"
name="panel" title="Right Panel" /></td>
</tr>
</table>
</body>
</html>
The following is the code for panel.jsp
<%@ taglib uri="http://www.opensymphony.com/sitemesh/decorator" prefix="decorator" %>

<table border="0" cellpadding="1px" cellspacing="2px">
<tr>
<th class="panelTitle">
<decorator:title default="Panel Title here" />
</th>
</tr>
<tr>
<td class="panelBody">
<decorator:body />
</td>
</tr>
</table>

The paneldata.html is a simple html page shown below:
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
</head>
<body>
Panel data goes here.
</body>
</html>

If you know tiles, this page is quite self explanatory. The main difference is the way in which this works. The decorator:body tag holds the actual page that is requested. This is made possible by the filter mapping in web.xml and the mapping of "/*" to main layout in decorators.xml file. Whereas in tiles, you have to push the pages into the template file, SiteMesh pulls the requested page into the template (this is not true in the case of applyDecorator though).

Thursday, November 02, 2006

The Struts 2.0 Controller

The major difference in architecture of Struts 2.0 is in the controller. Instead of the controller servlet of Struts 1.x (ActionServlet), Struts 2.0 introduces a Servlet Filter (FilterDispatcher). The filter has to be configured in the web.xml, as follows
<filter>
<filter-name>struts2</filter-name>
<filter-class>org.apache.struts2.dispatcher.FilterDispatcher</filter-class>
</filter>

<filter-mapping>
<filter-name>struts2</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
You don't have to declare a tag library as it is included in struts-core.jar. Using filters in a web application has many advantages, such as:
  • You can cascade functionality in multiple Filters, without modifying the code in the rest of the app.
  • Filters can wrap the request and response they hand on to the rest of the app, adding additional functionality there.
  • Filters could be used to perform pre-processing on the request, and/or post-processing on the response, to perform data transformations required by the application.
  • Filters can be used to enforce "users do not have direct access to a JSP page"
  • Filters can let you use existing servlets be used as Actions, without giving up things like the form bean processing.
  • Filters can, in effect, "remap" request URIs by doint a RequestDispatcher.forward() to the new target.
  • Filters apply to requests for static content, as well as requests to the controller servlet and JSP pages, so you can do extra processing around them as well.
Using a servlet filter instead of a Servlet has a few interesting and useful consequences such as allowing better integration with other products, by adding additional filters to aid the FilterDispatcher. For example: The Controller can clean-up the Action Context to avoid any memory leaks. But sometimes, the controller may not integrate well with some products, in which case a new filter can be created and used in a chain to ensure proper integration. ActionContextCleanUp is a filter used to work with the FilterDispatcher to allow better integration with SiteMesh. SiteMesh is a page decorator tool (like tiles) from OpenSymphony. In order to user SiteMesh with Struts 2.0, you have to define an additional filter in your web.xml file. Thus, when using SiteMesh, your web.xml filters would look like this:
<filter>
<filter-name>struts-cleanup</filter-name>
<filter-class>org.apache.struts2.dispatcher.ActionContextCleanUp</filter-class>
</filter>
<filter>
<filter-name>sitemesh</filter-name>
<filter-class>org.apache.struts2.sitemesh.VelocityPageFilter</filter-class>
</filter>
<filter>
<filter-name>struts</filter-name>
<filter-class>org.apache.struts2.dispatcher.FilterDispatcher</filter-class>
</filter>

<filter-mapping>
<filter-name>struts-cleanup</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
<filter-mapping>
<filter-name>sitemesh</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
<filter-mapping>
<filter-name>struts</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>

Wednesday, November 01, 2006

Weblogic Split Directory Environment

The WebLogic split development directory environment consists of a directory layout and associated Ant tasks that help you repeatedly build, change, and deploy J2EE applications. Using the split directory structure speeds-up the deployment time by avoiding unnecessary copying of files. In the split directory structure, the application directories are split into source and build directories.
  • The source directory contains the Java source files, deployment descriptors, JSPs etc. along with static content.
  • The build directory contains files generated during the build process.
The source directory is organized as follows:

root (represents the ear)
|_ EJB Modules/web modules
|_ Application Deployment descriptor (application.xml)
|_ Shared utility classes
|_ Common libraries shared by the different modules.
The split development directory structure requires each project to be staged as a J2EE Enterprise Application. BEA recommends that you stage even stand-alone Web applications and EJBs as modules of an Enterprise application, to benefit from the split directory Ant tasks.

Deploying from a Split Development Directory
All WebLogic Server deployment tools (weblogic.Deployer, wldeploy, and the Admin Console) support direct deployment from a split development directory. When an application is deployed to WebLogic Server, the server attempts to use all classes and resources available in the source directory for deploying the application. The server looks in the build directory only for the resources not available in the source directory.

Ant Tasks
The following is a list of Ant tasks that help you deploy applications using the split development directory environment.
  • wlcompile—This Ant task compiles the contents of the source directory into subdirectories of the build directory.
  • wlappc—Used to generate JSPs and container-specific EJB classes for deployment.
  • wldeploy—Deploys any format of J2EE applications (exploded or archived) to WebLogic Server. To deploy directly from the split development directory environment, you specify the build directory of your application.
  • wlpackage—Used to generate an EAR file or exploded EAR directory from the source and build directories.
After you set up your source directory structure, use the weblogic.BuildXMLGen utility to create a basic build.xml file. The syntax for weblogic.BuildXMLGen is as follows:
java weblogic.BuildXMLGen [options] 
After running weblogic.BuildXMLGen, edit the generated build.xml file to specify properties for your development environment.

Summary
The following steps illustrate how you use the split development directory structure to build and deploy a WebLogic Server application.
  1. Create the main EAR source directory for your project. When using the split development directory environment, you must develop Web Applications and EJBs as part of an Enterprise Application, even if you do not intend to develop multiple J2EE modules.
  2. Add one or more subdirectories to the EAR directory for storing the source for Web Applications, EJB components, or shared utility classes.
  3. Store all of your editable files (source code, static content, editable deployment descriptors) for modules in subdirectories of the EAR directory.
  4. Set your WebLogic Server environment by executing either the setWLSEnv.cmd (Windows) or setWLSEnv.sh (UNIX) script. The scripts are located in the WL_HOME\server\bin\ directory, where WL_HOME is the top-level directory in which WebLogic Server is installed.
  5. Use the weblogic.BuildXMLGen utility to generate a default build.xml file for use with your project. Edit the default property values as needed for your environment.
  6. Use the default targets in the build.xml file to build, deploy, and package your application.

Celebrate Eclipse's 5th Birthday

More details at eclipse.org

Monday, October 30, 2006

Strecks 1.0 released

Strecks a set of Java 5-specific extensions Struts framework, was released from beta on friday. Strecks, is annotation based and adds a number of modern features to Struts-based applications, including POJO actions, dependency injection, declarative validation and data binding, interceptors, pluggable views, as well as seamless Spring integration. It is also highly extensible and amenable to test driven development. The following is a brief list of features available in Strecks 1.0:
  • Pure POJO action beans with zero framework dependencies
  • Annotation-based dependency injection (typed request parameters, session attributes, Spring beans, and many others)
  • Converters and validators type-parameterized using Java 5 generics
  • Mechanisms for facilitating use of redirect after post pattern
  • Support for rendering using Spring MVC Views and View Resolvers
  • Pre- and post- action interceptors, with access to dependency resolved action beans as well as full runtime context
  • Works on the unchanged Struts 1.2.x and 1.3.x code bases.
  • Actions, form validation and data conversion easily testable with plain unit tests, with no additional test libraries required.

Friday, October 27, 2006

Struts 2: Info and Resources

Struts has been the most popular web application framework for the past few years. With this popularity have come enhancements and changes due not only to the changing requirements, but also to provide features available in newer frameworks. The new version Struts 2.0 is a combination of the Sturts action framework and Webwork. According to the Struts 2.0.1 release announcement, some key changes are:
  • Improved Design - All Struts 2 classes are based on interfaces. Core interfaces are HTTP independent.
  • Intelligent Defaults - Most configuration elements have a default value that we can set and forget.
  • Enhanced Results - Unlike ActionForwards, Struts 2 Results can actually help prepare the response.
  • Enhanced Tags - Struts 2 tags don't just output data, but provide stylesheet-driven markup, so that we can create consistent pages with less code.
  • First-class AJAX support - The AJAX theme gives interactive applications a significant boost.
  • Stateful Checkboxes - Struts 2 checkboxes do not require special handling for false values.
  • QuickStart - Many changes can be made on the fly without restarting a web container.
  • Easy-to-test Actions - Struts 2 Actions are HTTP independent and can be tested without resorting to mock objects.
  • Easy-to-customize controller - Struts 1 lets us customize the request processor per module, Struts 2 lets us customize the request handling per action, if desired.
  • Easy-to-tweak tags - Struts 2 tag markup can be altered by changing an underlying stylesheet. Individual tag markup can be changed by editing a FreeMarker template. No need to grok the taglib API! Both JSP and FreeMarker tags are fully supported.
  • Easy cancel handling - The Struts 2 Cancel button can go directly to a different action.
  • Easy Spring integration - Struts 2 Actions are Spring-aware. Just add Spring beans!
  • Easy plugins - Struts 2 extensions can be added by dropping in a JAR. No manual configuration required!
  • POJO forms - No more ActionForms! We can use any JavaBean we like or put properties directly on our Action classes. No need to use all String properties!
  • POJO Actions - Any class can be used as an Action class. We don't even have to implement an interface!
The following are a few resources to get started with writing Struts 2.0 applications

Popular Posts