Download as pdf or txt
Download as pdf or txt
You are on page 1of 31

Apache Geronimo and the Spring Framework, Part

6: Spring MVC: Using Web view technologies


Skill Level: Intermediate

Arun Chhatpar (arunchhatpar@gmail.com)


Software Architect
OmniViz

23 Jan 2007

This tutorial, the final installment in a six-part series, shows you how to use
Java™Server Pages (JSP), Velocity, Tiles, and PDF export using the Spring
Framework. You'll experiment with the V in Model-View-Controller (MVC) -- the
various Web views built into the Spring MVC. Along with this solid introduction to the
various view technologies supported by the Spring MVC, you'll see how easy these
technologies are to implement in the sample Phonebook application you've been
building throughout this series.

Section 1. Before you start


This tutorial series is for Java Platform, Enterprise Edition (Java EE) developers who
want to learn more about the Spring Framework and how to make use of its powerful
features on the Apache Geronimo application server.

About this series


This six-part tutorial series introduces you to the Spring Framework and how it fits in
with Geronimo. You began by examining the different Spring Framework
methodologies and how each works with the Geronimo server. You'll develop and
deploy a personal phonebook application throughout the series. The application will
include the following functionality:

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 1 of 31
developerWorks® ibm.com/developerWorks

• Showing the phonebook


• Showing details of each entry
• Adding new entries to the phonebook
• Editing, modifying, and deleting an entry
• Adding more details to the entry, such as primary e-mail addresses
Part 1 introduced each module of the Spring Framework and how each relates to the
development of Java EE applications on the Geronimo application server. It also
explained the methodologies that the Spring Framework is based on.

Part 2 covered how to build your first bare-bones application using the Spring
Framework on Geronimo.

Part 3 showed you how to extend the Geronimo application from Part 2 by adding
Java Database Connectivity (JDBC) support via the Derby database. You saw how
to integrate Object Relational Mapping (ORM) to your application using iBATIS.

Part 4 introduced you to Spring AOP and the Spring Web Framework. With the
Spring AOP, any object managed by the Spring Framework can become aspect
oriented, and this tutorial relies on the declarative transaction management services
provided via the Spring AOP.

Part 5 examined Spring MVC and got you started with the Spring MVC by
introducing you to its MVC framework and Web views.

This final installment, Part 6, shows you how to use JSP, Velocity, Tiles, and PDF
export using the Spring Framework. You get to experiment with various Web views
built into the Spring MVC.

About this tutorial


As mentioned above, Part 5 of this tutorial series provided a thorough introduction to
the Spring MVC module. You learned about different controllers offered by the
Spring MVC -- the C from MVC. This tutorial examines different view technologies --
the V from MVC.

One of the biggest challenges that Web application developers face is creating an
adaptable design. Making your views component flexible is particularly challenging.
Because Spring's support for views is so robust, this challenge is more manageable.
The use of JSPs, Tiles, Velocity, and PDF export in this tutorial is designed to
demonstrate how the Spring MVC API makes this possible.

JSPs and Velocity are two complementary view technologies. You can create views

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 2 of 31
ibm.com/developerWorks developerWorks®

using either one, each with its own set of advantages and disadvantages. This
tutorial demonstrates how easy it is to replace one with the other in the sample
Phonebook application.

You begin by reviewing JSP support in Spring MVC and then looking at Tiles, a very
good templating engine for view layout management. Tiles makes it easy to manage
your Web page layout, and Spring has built-in support for Tiles. You'll make use of
these classes to change the Web layout of the Phonebook application.

Next you'll replace the use of JSPs by using views defined with the Velocity
templating engine. Velocity makes it easy to access Java objects in your views
without complex definitions and Java constructs, such as Try Catch loops.

Finally, you get a look at rendering the Phonebook application's home page to be
displayed as a PDF file. Spring takes care of all the cumbersome and complex code
and logic needed to create a PDF. It gives you a clean API to work on the content,
without confusing you with PDF details.

Prerequisites
To follow along with this tutorial you should have a basic understanding of:

• Object-oriented programming
• Java Platform, Enterprise Edition (Java EE) terminology
• SQL statements
• XML semantics
• JSP tags, tag libraries, and tag library descriptors
An understanding of MVC is a plus, and a working knowledge of Velocity is also
highly advantageous, but isn't required.

System requirements
You need the following tools to follow along:

• The Spring Framework v1.2.8 -- You'll be using the compressed file with
all dependencies.
• Apache Geronimo 1.1 -- Geronimo is a Java 2 Platform, Enterprise
Edition (J2EE)-certified application server from Apache.
• Apache Derby database -- This tutorial uses Derby, which is an open

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 3 of 31
developerWorks® ibm.com/developerWorks

source lightweight database. Derby is embedded within Geronimo 1.1, so


no separate installations are required.
• Velocity JAR files -- You'll need the JAR files from the Velocity Template
engine. You can either copy them form your Spring Framework
installation or download it from the Velocity site.
• iText -- This is the PDF library used to generate PDFs on the fly. Spring
uses this library to generate PDFs, and it's part of the Spring Framework.
• Struts -- This is the Tiles support from Spring that's dependent on the
Struts API. You need the main struts.jar file from this API, which can be
found in the Spring Framework.
• Commons library JAR files needed by Spring Tiles support -- You need
commons-digester.jar, commons-collection.jar, and
commons-beanutils.jar. These all come with the Spring Framework
installation, so just copy them into your development environment.
• Standard taglibs API -- Because you'll be using JSP Standard Tag Library
(JSTL) tags in your JSPs, you need the JAR files from this compressed
file.
• Standard JSTL library -- The current release is 1.1.2.
• Apache Ant -- Make sure that Ant is configured properly and that its /bin
directory is in your Path system variable.
• Java 1.4.2 -- Make sure Java is installed and running on your system.
Install and configure the software

This section contains instructions for installing and configuring the software required
to develop, deploy, and run the example application.

1. Spring Framework and Geronimo installation: For the sample code to


run, you need a working installation of both Geronimo and the Spring
Framework. (Refer to Part 2 in this series for installation instructions.)

2. JAR files needed to resolve Tiles dependencies: The following JAR


files are needed by Tiles support in Spring:
• Struts.jar -- <SPRING_HOME>\lib\struts
• Commons-digester.jar -- <SPRING_HOME>\lib\jakarta-commons
• Commons-collection-3.2.jar --
<SPRING_HOME>\lib\jakarta-commons
• Commons-beanutils.jar -- <SPRING_HOME>\lib\jakarta-commons

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 4 of 31
ibm.com/developerWorks developerWorks®

All of these JAR files come bundled with the Spring Framework
installation package. You can find them in the directories indicated in the
above list, next to the .jar file name. Make sure to copy all of these JAR
files into the <WORKSPACE>/phonebook/lib directory.

3. JAR files needed to resolve Velocity dependencies: The sample


Phonebook application needs to include velocity-1.4.jar to work with
Velocity. Velocity also needs the commons-collections.jar you copied for
Tiles integration. The Velocity .jar file can be found in the Spring
installation directory in <SPRING_HOME>\lib\velocity folder. Make sure to
copy this into your <WORKSPACE>/phonebook/lib directory.

4. JAR files needed to resolve PDF dependencies: Spring's PDF support


API makes use of iText PDF library, so you need that for creating PDFs
for your application. Like the other JAR files, this one also comes
prepackaged with the Spring installation. You can find the itext-1.3.jar file
in <SPRING_HOME>\lib\itext. Copy this in the lib directory as well.

5. Installing Standard Taglibs from Apache and the Spring taglib: You'll
use the JSPs defined in Part 5 of this tutorial series and extend your
application using them, so you need to install JSTL libraries. (Refer to the
installation instructions in Part 5 of this series.)

6. Data model definition and database setup for your application: You'll
use the same Derby database that you created in other parts of this
tutorial series. The data model is also the same. If you created the
database and tables in Part 3, 4, or 5, then you should be all set. If not,
please follow instructions from Part 3 to take care of that first.

Section 2. Introduction to different view technologies


supported by Spring
One of the areas where the Spring Framework proves its prowess is in the
separation of view technologies from the rest of the MVC framework and its ability to
allow developers to change view technologies almost on the fly. For example, if you
want to use Velocity in place of JSPs, it's a simple matter of tweaking some
configuration files. In this section, you'll look at how Geronimo applications can
benefit from using these technologies with the Spring Framework.

Support for JSPs

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 5 of 31
developerWorks® ibm.com/developerWorks

Part 5 demonstrated Spring Framework's extensive support for JSPs. Spring


provides out-of-the-box controllers that you can use or extend, depending on your
application's needs. Spring MVC makes it easy for you to concentrate on content
rather than worry about implementation and integration details. Part 5 gave you a
great example of this. You defined controllers for actions in your Web pages, and
then these controllers returned JSP views based on those actions.

Using JSPs instead of servlets in your Geronimo applications makes it easy to


manage content for your Web application.

Tiles
Tiles is a templating engine built into the Apache Struts framework. Some of the
important features provided by Tiles include:

• The ability to create screens/views by assembling Tiles: header, footer,


menu, body, and so on.
• The definitions can be centralized in an XML file or directly into JSP
pages. This example uses a centralized XML file for view definitions.
• The ability to inherit a definition and extend another one or override
parameters.
• The ability to use Tiles as a layout manager and even reuse layouts for
different applications.
• The ability to easily create internationalized content using the Tiles API.
Spring MVC provides a simple framework with which to integrate Tiles into your Web
application. The most important use of Tiles is as a Web layout manager. Tiles
simplifies changing the layout of your view without changing any of your JSP pages.
The example application in this tutorial shows you how to define a layout and use it
in different pages.

Tiles is also beneficial to you if your Geronimo application's views use similar view
components in multiple pages. For example, if all your pages need to have the same
header and footer, or even a same left menu, then you can define these as Tiles and
use the Tiles API as a layout manager.

Velocity
Velocity, another templating engine based on Java technology, allows objects
defined in Java code to be referenced from views. One of the primary goals of
Velocity is to provide an alternate and simpler view technology to JSP view

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 6 of 31
ibm.com/developerWorks developerWorks®

technology by attempting to eliminate the complex use of JSP tags and Java
constructs like Try Catch loops.

Velocity also allows Web designers to work in parallel with application developers
based on the MVC model. Web page designers can focus solely on creating the site,
and programmers can focus on application code, because Velocity separates Java
code from the Web pages, making the pages more maintainable.

Figure 1 shows the basic MVC pattern using Velocity as the view technology.

Figure 1. Velocity providing the V in MVC

Views are created as Velocity templates, or .vm files. You can pass Java objects as
references to these views. You'll see how this works in later sections of this tutorial.

Clean and maintainable JSPs are a major benefit of using Velocity as a view
technology for your Geronimo applications. Velocity views contain the HTML that
represents the Web page view, with minimal reference to Java objects.

PDF export
Generating PDFs for Web views has always been a challenge for Web application
developers. Creating the PDF alone involves a cumbersome set of steps, and this
doesn't even take into account the difficulty in adding content. Spring MVC's PDF

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 7 of 31
developerWorks® ibm.com/developerWorks

support simplifies the process considerably. It takes care of all the intricate steps
involved in creating PDFs and provides a streamlined API to add content into it.

Spring's PDF support makes it easy to export your page views as PDFs in your
Geronimo application.

Now that you've laid the groundwork for the various technologies covered in this
tutorial, it's time to integrate them into the Phonebook application.

Section 3. Extending the Phonebook application to use


different view technologies
In this section, you begin by providing an overview of how you'll be integrating the
view technologies covered in the previous section into your example Phonebook
application. Then you can move on to the actual implementation.

Integrate the various view technologies into the Phonebook


application
Tiles integration includes the following steps:

• Define a layout mechanism for your application. This is a simple Web


application, so it will be header > body > footer.
• Define Tiles template files.
• Define View resolvers for Tiles templates.
• Extend this pattern to all pages of your Phonebook application.
Velocity integration includes the following steps:

• Define a new controller to handle Velocity template requests.


• Create a Velocity template for your home page.
• Define a View resolver for .vm files.
PDF generation includes the following steps:

• Define a controller to handle requests for PDF views.

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 8 of 31
ibm.com/developerWorks developerWorks®

• Define a view class to create the PDF for your Phonebook home page.
• Add this to the view resolver chain in Application Context.

Directory structure of your workspace


Figure 2 shows how the application is laid out. As you've been doing throughout this
series, download the source compressed file that came with this tutorial (see the
Downloads section) and extract it.

Figure 2. Directory structure of the application after extracting the source file

As you can see in the directory structure listed in Figure 2, there are no new

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 9 of 31
developerWorks® ibm.com/developerWorks

controllers for Tiles -- it's all about configuration. In the following sections, you'll find
out how Spring makes this possible.

What's going to happen here?


If you've been following this series so far, you've been working on creating a
Phonebook application. More functionality has been added with each installment.
Thus far your application allows you to:

• Show Phonebook entries (home page by default).


• Add an entry to the Phonebook.
• Delete a selected entry.
• Modify a selected Phonebook entry.
First, you'll convert your existing Phonebook application to use Tiles as the layout
manager. You start by defining your Web page layout in the Phonebook template, a
JSP. The Tiles view definition file will have definitions of specific views to be
included in this Phonebook template.

Figure 3 gives you an idea of how to define your layout using Tiles.

Figure 3. Directory structure of the application after unzipping the source file

As you can see, Tiles acts as the layout manager and the individual implementation

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 10 of 31
ibm.com/developerWorks developerWorks®

pages are considered JSP Tiles. The layout manager can place the Tiles in
whatever way you want as long as the template elements are provided an
implementation page via a definition.

Next, see how you can replace the JSPs with views defined in Velocity by just
changing some configurations in the Application Context file. For this tutorial, you'll
change the home page to be replaced by the Velocity template. You can use it as an
exercise to convert the rest of the pages to Velocity views.

The final part of your application shows you how to create a PDF view using the
AbstractPdfView class from Spring MVC. This class takes care of all the work of
creating the PDF document for you and gives you a clean document to add your
content to. Then you'll manually create the Phonebook home page and return it as a
PDF.

Note: Spring MVC's PDF support is not like a screen grabber for Web pages; there
are other tools available for that purpose. You have to manually create a view that
you want to export in the PDF document.

Integrate Tiles into your application


Your Phonebook application has been developed using JSPs so far. The best way to
see Tiles working with your application is to use it as a layout manager. The
following sections show you how.

Add the Tiles tag library to your application

As with any other JSP tag library, you must add the Tiles library to the Web
application deployment descriptor before you can use it. Just add the taglib element
in Listing 1 to your web.xml file.

Listing 1. Add Tiles tag library in web.xml

<jsp-config>
<taglib>
<taglib-uri>/tiles</taglib-uri>
<taglib-location>/WEB-INF/struts-tiles.tld</taglib-location>
</taglib>
</jsp-config>

Now you need to define the layout of your Web application.

Define a template layout in Phonebook-layout.jsp


In the context of Tiles definitions, a template is a JSP page that uses a JSP custom

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 11 of 31
developerWorks® ibm.com/developerWorks

tag library to describe the layout of a page. It defines how the pages of your
application will look without specifying the content. The content will be inserted at
run time. As you can see, it's a simple template; you define your default page
structure to be Header > Body > Footer. Listing 2 shows the code for this JSP.

Listing 2. phonebook-layout.jsp shows how your Web pages are laid out

<%@ taglib prefix="tiles" uri="/tiles" %>


<!-- This page defines the general layout for Phonebook Application Pages -->
<tiles:insert name="header"/>
<tiles:insert name="body"/>
<tiles:insert name="footer"/>

You'll use this same template for all your pages. It's using the tiles:insert tag to
insert contents represented by the name attribute. As you can see here, there's no
content, only the layout of the page.

Now you need to associate views to Tiles view names, which you'll do next.

Configure Tiles to work with Spring


To be able to use Tiles with the Spring MVC, you have to configure it using files
containing view definitions. In Spring you do this using the TilesConfigurer
class. Listing 3 shows how this is defined in the Application Context file.

Listing 3. The views definition file name is passed to TilesConfigurer in


Application Context

<!-View Resolver for Tiles -->


<bean id="tilesViewResolver"
class="org.springframework.web.servlet.view.ResourceBundleViewResolver">
<property name="order" value="1" />
<property name="basename" value="views-phonebook-tiles"/>
</bean>
<!-- Tiles configurer reads the view definition from the XML file -->
<bean id="tilesConfigurer"
class="org.springframework.web.servlet.view.tiles.TilesConfigurer">
<property name="factoryClass"
value="org.apache.struts.tiles.xmlDefinition.I18nFactorySet"/>
<property name="definitions">
<list>
<value>/WEB-INF/defs/phonebook-definitions.xml</value>
</list>
</property>
</bean>

You can see that the name of your view definition file is phonebook-definitions.xml.
The TilesConfigurer reads this file at initialization and then makes all the views

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 12 of 31
ibm.com/developerWorks developerWorks®

from your definition file available to be used in your application.

The other bean definition is for ViewResolver, which Spring should use to resolve
your view. The ResourceBundleViewResolver is one of the most commonly
used view resolvers from the Spring Framework. You need to pass in the properties
file that defines the view names that are mapped to a class and a URL. Listing 4
shows the contents from your views-phonebook-tiles.properties file.

Listing 4. View definitions in views-phonebook-tiles.properties file

home-mvc.class=org.springframework.web.servlet.view.tiles.TilesView
home-mvc.url=home-mvc
addentry-mvc.class=org.springframework.web.servlet.view.tiles.TilesView
addentry-mvc.url=addentry-mvc
modifyentry-mvc.class=org.springframework.web.servlet.view.tiles.TilesView
modifyentry-mvc.url=modifyentry-mvc

The definition in Listing 4 tells the Spring MVC module that you have three views in
your application, and each one is a TilesView. The second line shows the URL
specific to each page representing these views.

Next you'll see how to inject actual views implemented by specific JSPs into your
Tiles layout.

Associate views to actual JSP implementations

The layout tile shown in Listing 2 is generic and will be used by all of your Web
pages. It doesn't know anything about the home, addEntry, or ModifyEntry JSP
page contents. This is by design, as it lets you reuse this layout for many pages.
Instead of hardcoding the content in the layout definition page, it's passed as
parameters to the layout page at run time.

In Spring, you do this by defining an XML definitions file. Listing 5 shows how it's
done in your Phonebook application.

Listing 5. Definitions file for passing content in to layout page at run time

<tiles-definitions>
<!-- DEFAULT MAIN TEMPLATE -->
<definition name="template"
page="/WEB-INF/jsp/phonebook-layout.jsp">
<put name="header"
value="/WEB-INF/jsp/header.jsp"/>
<put name="footer"
value="/WEB-INF/jsp/footer.jsp"/>
</definition>
<!-- The Home Page -->
<definition name="home-mvc" extends="template">

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 13 of 31
developerWorks® ibm.com/developerWorks

<put name="body" value="/WEB-INF/jsp/home-mvc.jsp"


type="page"/>
</definition>
<!-- The Add Entry Page -->
<definition name="addentry-mvc" extends="template">
<put name="body" value="/WEB-INF/jsp/addentry-mvc.jsp"
type="page"/>
</definition>
<!-- The Modify Entry Page -->
<definition name="modifyentry-mvc" extends="template">
<put name="body" value="/WEB-INF/jsp/modifyentry-mvc.jsp"
type="page"/>
</definition>

</tiles-definitions>

The first definition defines a default template by giving it a name and a page that
contains the content for that template. If you go back to Listing 2, where you defined
the layout for your application in phonebook-layout.jsp, you'll notice that the name of
the views inserted in that layout are the same as those defined in this template. So
you're essentially associating content to the template in these definitions here.

The put elements in the template definition tell the Tiles framework where to get the
views from. In your case, the header view gets its content from header.jsp, and the
footer gets it from footer.jsp.

The next Tiles definition defines your home page. It extends the default template and
just injects the body into the home-mvc.jsp page. If you look at this definition
carefully, you'll see how your home page gets built. Here's what happens:

• Because home-mvc extends the default template, it automatically gets the


header and footer components from the Phonebook layout.
• This definition puts the body into home by pointing to the home-mvc.jsp
page.
The Spring MVC framework brings all the JSPs together at run time and passes the
content back to the client as a single page. This is a clean, simple way to write your
Web application.

Build and run it


The easiest and fastest way to see this running is to deploy the phonebook.war file
using the Geronimo Web Console. You can follow directions to deploy the .war file
from Part 2. After you've deployed the .war file, point your browser to
http://localhost:8080/phonebook/home-mvc.act to see this Tiles-enabled application
in action. Figure 4 shows what the home page looks like after you've executed it.

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 14 of 31
ibm.com/developerWorks developerWorks®

Figure 4. Tiles-enabled home page as seen in your browser

Now that you've seen Tiles in action with the Spring Framework on the Geronimo
application server, you can move on to integrating Velocity into your application.

Section 4. Integrating Velocity into your application


This section shows how you can replace JSPs with views defined using Velocity --
also known as Velocity views, or .vm files. Learn how easy it is to change view
technologies by making changes to configuration files only. Your Web application
needs to include the velocity.x.jar file to work with Velocity (see Prerequisites), so
make sure you have copied that .jar file into the WEB-INF/lib directory.

Configure Velocity into Spring's Application Context

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 15 of 31
developerWorks® ibm.com/developerWorks

There are two ways you can make ApplicationContext aware of your Velocity
templates. The first one is using the VelocityConfigurer. All you need to do is
provide the location of your Velocity templates in resourceLoaderPath, and the
VelocityConfigurer makes all the templates from that location available to your
application at run time.

The other (and preferred) way is to define your own controller and then use that to
locate your views. Listing 6 shows these bean definitions in the
phonebook-servlet.xml file.

The first two bean definitions define that a request for home.vel page should be
controlled by the PhonebookVelocityController class. You'll be defining this
class in the following sections. The third bean definition uses the
VelocityViewResolver to resolve any page requests with a .vm extension.

Listing 6. Bean definitions that make your context aware of Velocity views

<bean id="urlMapping"
class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping">
<property name="mappings">
<props>
<prop key="/*.do">phonebookController</prop>
<prop key="/*.htm">phonebookFlowController</prop>
<prop
key="/*.flow">phonebookFlowController</prop>
<prop
key="/addentry-mvc.act">addEntryFormController</prop>
<prop
key="/home-mvc.act">phonebookHomeController</prop>
<prop
key="/modifyentry-mvc.act">modifyEntryFormController</prop>
<prop
key="/deleteentry-mvc.act">deleteEntryFormController</prop>
<prop
key="/home.vel">phonebookVelocityController</prop>
<prop
key="/home.pdf">phonebookPDFController</prop>
</props>
</property>
</bean>
<bean id="phonebookVelocityController"
class="phonebook.velocity.PhonebookVelocityController"/>
<!-- View Resolver for Velocity -->
<bean id="velocityViewResolver"
class="org.springframework.web.servlet.view.velocity.VelocityViewResolver"
>
<property name="cache" value="true"/>
<property name="prefix" value=""/>
<property name="suffix" value=".vm"/>
</bean>

Define a Velocity controller class

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 16 of 31
ibm.com/developerWorks developerWorks®

Why define a controller for Velocity in the first place? Remember that you populate
your home page with all the phonebook entries read from the database, and you
read this list from the database and pass it to the Velocity view as an object. The
Velocity engine passes this object to the home page template, which then iterates
through it using the Velocity Template Language tags. Listing 7 shows code for
PhonebookVelocityController.

Listing 7. Class that reads PhonebookEntries from the database and passes to
the view

public class PhonebookVelocityController implements Controller {


/** Creates a new instance of PhVelocityController */
public PhonebookVelocityController() {
}
public ModelAndView handleRequest(HttpServletRequest request,
HttpServletResponse response)
throws ServletException, IOException, Exception {
ModelAndView view = null;
if (request.getRequestURI().indexOf("home")!=-1) {
view = new ModelAndView("phonebook-template");
view.addObject("viewId", "home");
view.addObject("time", new Date() );
WebApplicationContext ctx =
WebApplicationContextUtils.getWebApplicationContext(request.getSession().
getServletContext());
IPhonebookDataProvider pb = (IPhonebookDataProvider)
ctx.getBean("phonebook");
List phonebookEntries = pb.getPhonebookEntries();
System.out.println("Velocity No. of Entries =
"+phonebookEntries.size());
view.addObject("phEntries", phonebookEntries);
}
return view;
}
}

You can see that the controller uses WebApplicationContext to get the
phonebook bean and reads the phonebook entries from the database. It then adds
this as an object to the view. You'll see how it's read by the Velocity template next.

Create a Velocity template for home view


As you did for your Tiles views, you define the default layout in a template file.
Listing 8 shows phonebook-template.vm.

Listing 8. The default template defining the layout of your Web application

#set ($viewName = ${viewId})

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 17 of 31
developerWorks® ibm.com/developerWorks

#set ($viewName = "${viewName}.vm") ## View name is passed in dynamically from controller.


#parse("header.vm")
#parse($viewName)
#parse("footer.vm")

You can see that your phonebook layout is the same. The Velocity engine reads this
template at run time, and the parse tag renders the components passed into it as
parameters. The viewName is passed in dynamically by the
phonebookVelocityController at run time.

Listing 9 shows the template code for the home page.

Listing 9. Template code for the Velocity-based home page

#set ($time1 = ${time})


#set ($phonebook = ${phEntries})
<html>
<script type="text/javascript">
function goToAddEntryPage() {
document.myForm.action="/phonebook/addentry.vel";
document.myForm.method="GET";
document.myForm.submit();
}
function setId(entryID, rowID) {
document.myForm.entryID.value = entryID;
document.myForm.rowID.value = rowID;
}
function noRowSelected() {
var entryID = document.myForm.entryID.value;
var rowID = document.myForm.rowID.value;
if (entryID == "" || rowID == "") {
return "true";
} else {
return "false";
}
}
function goToModifyEntryPage() {
if (noRowSelected() == "true") {
alert("Please select an Entry to Modify");
return;
}
document.myForm.action="/phonebook/modifyentry-mvc.act";
document.myForm.method="GET";
document.myForm.submit();
}
function deleteEntry() {
if (noRowSelected() == "true") {
alert("Please select an Entry to Delete");
return;
} else {
var retVal = confirm("Please click OK to confirm your deletion. Click
Cancel otherwise");

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 18 of 31
ibm.com/developerWorks developerWorks®

if (retVal != true) {
return;
}
}
document.myForm.action="/phonebook/deleteentry-mvc.act";
document.myForm.method="POST";
document.myForm.submit();
}
</script>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Phone Book - $time1 </title>
</head>
<body>
<!--The Heading of the Phone Book Page-->
<h1 align=center>Phone Book</h1>
<BR>
<BR>
<!-- The table containing phone book contents. -->
<TABLE border="1" width="100%">
<TH width="5%" align=center>Select</TH>
<TH width="25%" align=center>Name</TH>
<TH width="15%" align=center>Home Phone</TH>
<TH width="15%" align=center>Work Phone</TH>
<TH width="15%" align=center>Cell Phone</TH>
<TH width="25%" align=center>Email</TH>

#foreach( $pbEntry in $phonebook )


#set ($i = $velocityCount - 1)
<TR>
<TD align=center><input type=radio name="data_"$i
alt="Select to Delete" align="middle"></TD>
<TD align=center>$pbEntry.getFirstName()
$pbEntry.getLastName()</TD>
<TD align=center>$pbEntry.getHomeNumber()</TD>
<TD align=center>$pbEntry.getWorkNumber()</TD>
<TD align=center>$pbEntry.getCellNumber()</TD>
<TD align=center>$pbEntry.getEmail()</TD>
</TR>
#end
</TABLE>
<BR>
<BR>
<table align=center>
<!-- The row containing command buttons -->
<TR align=center>
<!--
<TD><input type=submit name="Add" value="Add an Entry"
onclick="javascript:goToAddEntryPage()"></TD>
<TD><input type=button name="Modify" value="Modify
Selected Entry"
onclick="javascript:goToModifyEntryPage()"></TD>
<TD><input type=button name="Delete" value="Delete
Selected Entry"
onclick="javascript:deleteEntry()"></TD>
-->
</TR>
</table>
</body>
<BR><BR><BR><BR><BR><BR>

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 19 of 31
developerWorks® ibm.com/developerWorks

</html>

This home.vm template definition uses Velocity Template Language (VTL), the
templating language for Velocity. The second line of this template takes the
pbEntries object passed in by your Velocity controller class. Then it's used to
iterate through the list populating the table with phonebook entries.

Note: This tutorial doesn't cover VTL in detail. Refer to the Velocity reference guide
to get in-depth information about this topic (see Resources for a link).

The final step in this process is to add a URL mapping for .vm requests.

Add URL mapping for *.vm requests


You should be familiar with the servlet mapping shown in Listing 10 by now.

Listing 10. URL Mapping for *.vm requests

<servlet-mapping>
<servlet-name>phonebook</servlet-name>
<url-pattern>*.vel</url-pattern>
</servlet-mapping>

That's all you need to do. Now let's see it in action!

Build and deploy it


As before, the easiest and fastest way to see this working is to deploy the
phonebook.war in the example package that comes with this tutorial (see Downloads
for a link) using the Geronimo Web console. Then point your browser to
http://localhost:8080/phonebook/home.vm to see the Velocity engine in action.

If everything goes fine, your browser page will look like the one shown in Figure 5.

Figure 5. Home page showing Velocity engine in action

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 20 of 31
ibm.com/developerWorks developerWorks®

The next section shows you how easy it is to return a PDF made from the contents
of a Web page using Spring MVC's PDF support.

Section 5. Exporting document views as PDFs


An HTML page is not always the best way to view model data, so Spring makes it
simple to generate PDF documents. This section shows you how to render the same
model you've been using so far as a PDF document and return it to the client with
the correct content type.

First you have to define a controller to get the list of phonebook entries from a
database table and pass it to the PDF view class, so start developing your PDF
controller.

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 21 of 31
developerWorks® ibm.com/developerWorks

Define PhonebookPDFController class


This class reads the phonebookEntries class using bean definitions from Spring
ApplicationContext and then passes it to the PDF view represented by the
PhonebookPdfView class. Listing 11 shows the code for this controller.

Listing 11. PhonebookPDFController class reads phonebook entries and


passes them to PhonebookPdfView class

public class PhonebookPDFController extends


MultiActionController {
private static final String PDF_VIEW = "phonebook_pdfView";
private String pdfView = PDF_VIEW;
/** Creates a new instance of PbPDFController */
public PhonebookPDFController() {
}

public void setPdfView(String view) {


this.pdfView = view;
}
/**
* Custom handler for phonebook PDF document.
* @param request current HTTP request
* @param response current HTTP response
* @return a ModelAndView to render the response
*/
public ModelAndView handlePdf(HttpServletRequest request,
HttpServletResponse response) throws ServletException, Exception {
WebApplicationContext ctx =
WebApplicationContextUtils.getWebApplicationContext(request.getSession().
getServletContext());
IPhonebookDataProvider pb = (IPhonebookDataProvider)
ctx.getBean("phonebook");
List phonebookEntries = pb.getPhonebookEntries();
return new ModelAndView(this.pdfView, "phonebook",
phonebookEntries);
}

The next logical step is to define the View class that actually generates the PDF
from your model output.

Define PDF View class


PhonebookPdfView subclasses the AbstractPdfView class to implement
custom generation of the PDF document specific to your Web view. The most

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 22 of 31
ibm.com/developerWorks developerWorks®

important method to note in this class is buildPdfDocument. This is where all the
magic happens. Listing 12 shows complete code for generating a PDF for the
Phonebook application.

Listing 12. PDF view class creates the PDF document

public class PhonebookPdfView extends AbstractPdfView {


private static final Font HEADLINE_FONT = new Font( Font.TIMES_ROMAN , 18,
Font.BOLD, Color.black );
private static final Font DATA_HEAD_FONT = new Font( Font.TIMES_ROMAN, 10,
Font.BOLD, Color.black );
private static final Font TEXT_FONT = new Font( Font.TIMES_ROMAN, 8,
Font.NORMAL,
Color.black );
private static final Font FOOTER_FONT = new Font( Font.TIMES_ROMAN, 5,
Font.NORMAL,
Color.black );
private static final int NO_OF_COLUMNS = 5;

/** Creates a new instance of PhonebookPdfView */


public PhonebookPdfView() {
}
protected void buildPdfMetadata(Map model, Document document,
HttpServletRequest request) {
document.addTitle("Phone Book");
document.addCreator("Arun Chhatpar");
}

protected void buildPdfDocument(


Map model,
Document doc,
PdfWriter writer,
HttpServletRequest req,
HttpServletResponse resp)
throws Exception {
List phonebook = (List) model.get("phonebook");
String title = "Phone Book";
Paragraph h1 = new Paragraph(title, HEADLINE_FONT);
h1.setAlignment(Paragraph.ALIGN_CENTER);
doc.add(h1);
doc.add(new Paragraph(" "));
doc.add(new Paragraph(" "));
doc.add(new Paragraph(" "));
// We create a table for used criteria and extracting information
PdfPTable table = new PdfPTable(NO_OF_COLUMNS);
int headerwidths[] = {20, 20, 20, 20, 20};
table.setWidths(headerwidths);
table.setWidthPercentage(100);
table.getDefaultCell().setBorderWidth(1);
table.getDefaultCell().setBorderColor(Color.black);
table.getDefaultCell().setPadding(3);
table.getDefaultCell().setHorizontalAlignment(Element.ALIGN_CENTER);
table.getDefaultCell().setVerticalAlignment(Element.ALIGN_MIDDLE);
table.addCell(new Phrase("Name", DATA_HEAD_FONT));
table.addCell(new Phrase("Home Phone", DATA_HEAD_FONT));
table.addCell(new Phrase("Work Phone", DATA_HEAD_FONT));
table.addCell(new Phrase("Cell Phone", DATA_HEAD_FONT));

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 23 of 31
developerWorks® ibm.com/developerWorks

table.addCell(new Phrase("Email", DATA_HEAD_FONT));


// We set the above row as title
// and adjust properties for normal cells
table.setHeaderRows(1);
table.getDefaultCell().setBorderWidth(1);
// We iterate now on the Phonebook list
Iterator it = phonebook.iterator();
while(it.hasNext()) {
PhonebookEntry pEntry = (PhonebookEntry) it.next();
table.addCell(new Phrase(pEntry.getFirstName() + " " +
pEntry.getLastName(),
TEXT_FONT));
table.addCell(new Phrase(pEntry.getHomeNumber(), TEXT_FONT));
table.addCell(new Phrase(pEntry.getWorkNumber(), TEXT_FONT));
table.addCell(new Phrase(pEntry.getCellNumber(), TEXT_FONT));
table.addCell(new Phrase(pEntry.getEmail(), TEXT_FONT));
}
doc.add(table);
doc.add(new Paragraph(" "));
doc.add(new Paragraph(" "));
doc.add(new Paragraph(" "));
doc.add(new Paragraph(" "));

String footerStr1 = "This example is developed to demonstrate the Spring


framework on the Geronimo Application Server.";
String footerStr2 = "This example is designed purely for
demonstrating the capabilities of the framework. It should under no
circumstances be used for production use.";
Paragraph footer1 = new Paragraph(footerStr1, FOOTER_FONT);
footer1.setAlignment(Paragraph.ALIGN_CENTER);
doc.add(footer1);
Paragraph footer2 = new Paragraph(footerStr2, FOOTER_FONT);
footer2.setAlignment(Paragraph.ALIGN_CENTER);
doc.add(footer2);
}
}

As you can see, you have to manually create the content for the PDF document. But
Spring's support classes makes it so much easier!

The next step is to define the view resolver for PDF views.

View resolver for PDF views


View resolver for PDF views is similar to the view resolver definition for Velocity. You
might have noticed by now that you're using the MultiActionController for the
PDF controller class. The idea is to show you another way to handle and resolve
views in Spring. Listing 13 should look familiar to you.

Listing 13. Adding the PDF controller and resolver in ApplicationContext

<bean id="urlMapping"
class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping">
<property name="mappings">

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 24 of 31
ibm.com/developerWorks developerWorks®

<props>
<prop key="/*.do">phonebookController</prop>
<prop key="/*.htm">phonebookFlowController</prop>
<prop
key="/*.flow">phonebookFlowController</prop>
<prop
key="/addentry-mvc.act">addEntryFormController</prop>
<prop
key="/home-mvc.act">phonebookHomeController</prop>
<prop
key="/modifyentry-mvc.act">modifyEntryFormController</prop>
<prop
key="/deleteentry-mvc.act">deleteEntryFormController</prop>
<prop
key="/home.vel">phonebookVelocityController</prop>
<prop
key="/home.pdf">phonebookPDFController</prop>
</props>
</property>
</bean>

<bean id="phonebookPDFController"
class="phonebook.pdf.PhonebookPDFController">
<property name="methodNameResolver">
<bean
class="org.springframework.web.servlet.mvc.multiaction.
PropertiesMethodNameResolver">
<property name="mappings">
<props>
<prop
key="/home.pdf">handlePdf</prop>
</props>
</property>
</bean>
</property>
</bean>

<!-- View Resolver for PDF -->


<bean id="pdfViewResolver"
class="org.springframework.web.servlet.view.ResourceBundleViewResolver">
<property name="order" value="2" />
<property name="basename" value="views-phonebook-pdf"/>
</bean>

As before, the ResourceBundleViewResolver needs a properties file for class


and URL definitions for your view. In this case the views-phonebook-pdf.properties
file contains only one line:
phonebook_pdfView.(class)=phonebook.pdf.PhonebookPdfView.

If you see the controller class, the view it uses is the same as defined in this
properties class. This is how Spring associates this view class to that controller.

The final step is to add a URL mapping for PDF requests.

Add URL mapping for PDF requests


Listing 14 shows you how to add a URL mapping into your web.xml file to handle
*.pdf requests.

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 25 of 31
developerWorks® ibm.com/developerWorks

Listing 14. URL mapping for *.pdf in web.xml file

<servlet-mapping>
<servlet-name>phonebook</servlet-name>
<url-pattern>*.pdf</url-pattern>
</servlet-mapping>

Now it's time to build, deploy, and run the application so you can see it in action.

Build, deploy, and run it


The source compressed file that comes along with this tutorial (see Downloads for a
link) has all the classes, config files, and an Ant build file, if you want to build it. The
tutorial source also has a deployable .war file with everything you need in it. You can
use either method to get the phonebook.war file.

You also need to make sure that you have all the JAR files mentioned in the
readme.txt file in your <WORKSPACE>/phonebook/lib directory. Please read the
instructions in that file carefully, and make sure to copy all the required files into
<WORKSPACE>/phonebook/lib. Note: You can refer to build and pack instructions
in Part 2 of this tutorial series for more information on building and unpacking these
files.

Deploy the phonebook.war using the Deploy New tool in Geronimo. If everything
works as expected, You'll see a message on the Geronimo Web Console saying
Phonebook application deployed successfully. Next, point your browser
to the new page: http://localhost:8080/phonebook/home.pdf. If everything worked as
expected, you should see the PDF in Adobe Acrobat Reader in your browser.

Benefits of the Spring Framework


You've learned about various view technologies supported by the Spring Framework
in this tutorial. Most Web developers have learned from experience how important it
is to modularize Web content and layout. While JSP is a useful technology, it has
some inherent drawbacks, such as a lack of native support for layouts or layout
managers. Templating technologies like Tiles fill that void. Tiles provides an
excellent way to define the layout of your Web application in a single layout file,
which also makes it easy to change according to business needs. Here are some of
the benefits that Spring's support for these technologies brings to the table:

• Clear separation of views and the content that goes into these views
• The ability to separate tasks (using templates with Spring makes it easy
for application developers to concentrate completely on application code

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 26 of 31
ibm.com/developerWorks developerWorks®

and for Web developers to design the best HTML pages without worrying
about how they will be rendered)
• The ability to change view technologies dynamically
• The ability to test individual view components and pinpoint errors early in
the development cycle

Section 6. Summary
This tutorial has given you a solid introduction to the various view technologies
supported by the Spring MVC. You saw how easy it is to implement these
technologies in your sample Phonebook application. Spring's layered architecture
allows you to introduce only as much functionality as you think your application
needs, and allows you to add more as you get comfortable with a particular
technology.

Using templates to define and manage layouts for views is not new, but using this
technology with Spring is easy. You saw that Spring proves to be a great framework
for taking care of many complex issues for you while providing a simple way to
perform necessary tasks, such as creating PDFs.

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 27 of 31
developerWorks® ibm.com/developerWorks

Downloads
Description Name Size Download
method
Part 6 source code geronimo.spring6.source.zip 126KB HTTP
Part 6 WAR file geronimo.spring6.war.zip 7,149KB HTTP

Information about download methods

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 28 of 31
ibm.com/developerWorks developerWorks®

Resources
Learn
• The official Spring Reference Manual is a clean and simple way of learning
more about Spring Framework.
• "The Spring series, Part 1: Introduction to the Spring framework"
(developerWorks, June 2005) is another good introduction to the Spring
Framework.
• Check out the article "Simplify Your Web App Development Using the Spring
MVC Framework" to learn how to build a simple stock-trading Web applications
using the Spring Framework.
• Read " The Spring series, Part 3: Swing into Spring MVC" (developerWorks,
September 2005) for a good introduction to Spring MVC.
• Check out another helpful tutorial on Spring MVC basics.
• "Introduction to the Spring Framework" is a thorough write-up by one of the first
and most active members of the Spring design team.
• Peruse this documentation on how to deploy Spring Framework example
applications on Apache Geronimo.
• Get an introduction to classic transactions in "Tour Web Services Atomic
Transaction operations: Beginner's guide to classic transactions, data recovery,
and mapping to WS-AtomicTransactions" (developerWorks, September 2004).
• Read "Optimize your Apache Geronimo distribution" (developerWorks, May
2006) to learn to hone the deployment of your Apache Geronimo distribution to
the necessary core services and applications.
• Check out "Create, deploy, and debug Apache Geronimo applications"
(developerWorks, May 2005) to learn how to use the Eclipse plug-in for
Geronimo.
• Read Martin Fowler's seminal piece "Inversion of Control Containers and the
Dependency Injection pattern."
• Check out the developerWorks Apache Geronimo project area for articles,
tutorials, and other resources to help you get started developing with Geronimo
today.
• Find helpful resources for beginners and experienced users at the Get started
now with Apache Geronimo section of developerWorks.
• Check out the IBM® Support for Apache Geronimo offering, which lets you
develop Geronimo applications backed by world-class IBM support.

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 29 of 31
developerWorks® ibm.com/developerWorks

• Visit the developerWorks Open source zone for extensive how-to information,
tools, and project updates to help you develop with open source technologies
and use them with IBM's products.
• Browse all the Apache articles and free Apache tutorials available in the
developerWorks Open source zone.
• Browse for books on these and other technical topics at the Safari bookstore.
• Stay current with developerWorks technical events and webcasts.
• Get an RSS feed for this series. (Find out more about RSS.)
Get products and technologies
• Link to download the Spring Framework separately if you want to. You can also
check the Changelog to see what's changed in newer versions.
• Visit the Tomcat home page to learn more about the Tomcat Container. The site
also gives you lots of examples to learn how to deploy your Web applications in
Tomcat.
• Get the Apache Standard taglibs implementing JSTL 1.1.
• Download the latest version of Apache Geronimo.
• Innovate your next open source development project with IBM trial software,
available for download or on DVD.
• Download your free copy of IBM WebSphere® Application Server Community
Edition V1.0 -- a lightweight J2EE application server built on Apache Geronimo
open source technology that is designed to help you accelerate your
development and deployment efforts.
Discuss
• Participate in the discussion forum for this content.
• Stay up to date on Geronimo developments at the Apache Geronimo blog.
• Get involved in the developerWorks community by participating in
developerWorks blogs.

About the author


Arun Chhatpar
Arun Chhatpar has more than nine years of significant experience in
Java programming and client/server architectures, and is a Sun
Certified Enterprise Software Architect. He has been a lead designer
and developer for NBCi and is currently a software architect and lead

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 30 of 31
ibm.com/developerWorks developerWorks®

software engineer for OmniViz.

Trademarks
IBM, the IBM logo, and WebSphere are registered trademarks of IBM in the United
States, other countries, or both.
Java and all Java-based trademarks are trademarks of Sun Microsystems, Inc. in the
United States, other countries, or both.

Spring MVC: Using Web view technologies Trademarks


© Copyright IBM Corporation 2007. All rights reserved. Page 31 of 31

You might also like