Sunday, January 20, 2013

Using Spring with Velocity and SiteMesh on Google App Engine

When working with web applications, it's often important to pick a view technology that you like but also has long term support. The following will demonstrate how to integrate Velocity and SiteMesh into Spring and Google App Engine.

Tools:

  • Spring MVC 3.2.0
  • Google App Engine SDK 1.7.4
  • velocity-1.7
  • SiteMesh 2.4.2


We will be using Apache Velocity since Spring recommends it (Alternatively, you can use FreeMarker). We will also use SiteMesh because the decorator pattern to plug in header, footer, or other components are very convenient.

This tutorial will assume you have set up Spring on Google App Engine already. Read Running Spring 3.2 on Google App Engine for more details.

First download the following:



Add the following JARs to /war/WEB-INF/lib/

  • velocity-1.7.jar
  • velocity-1.7-dep.jar
  • sitemesh-2.4.2.jar
  • velocity-tools-view-2.0.jar
  • commons-collections-3.2.jar
  • commons-digester-2.1.jar
You may need to find some of the above elsewhere.

Add all these JARs to your build path.( Right Click on root project folder. Click Properties. Click Java Build Path. Click Libraries. Click Add JARs.)

In /war/WEB-INF/web.xml, add the following:
<filter>
<filter-name>sitemesh</filter-name>
<filter-class>com.opensymphony.sitemesh.webapp.SiteMeshFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>sitemesh</filter-name>
<url-pattern>/*</url-pattern>
<dispatcher>FORWARD</dispatcher>
<dispatcher>REQUEST</dispatcher>
<dispatcher>INCLUDE</dispatcher>
</filter-mapping>
<servlet>
<servlet-name>sitemesh-velocity</servlet-name>
<servlet-class>com.opensymphony.module.sitemesh.velocity.VelocityDecoratorServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>sitemesh-velocity</servlet-name>
<url-pattern>*.vm</url-pattern>
</servlet-mapping>
view raw gistfile1.xml hosted with ❤ by GitHub

In your serlvet.xml, replace your viewResolver with:
<bean id="velocityConfig"
class="org.springframework.web.servlet.view.velocity.VelocityConfigurer">
<property name="resourceLoaderPath" value="/velocity" />
</bean>
<bean id="viewResolver"
class="org.springframework.web.servlet.view.velocity.VelocityViewResolver">
<property name="cache" value="false" />
<property name="prefix" value="" />
<property name="suffix" value=".vm" />
<property name="exposeSpringMacroHelpers" value="true"/>
</bean>
view raw gistfile1.txt hosted with ❤ by GitHub

Create the file /war/WEB-INF/sitemesh.xml and add
<sitemesh>
<property name="decorators-file" value="/WEB-INF/decorators.xml"/>
<excludes file="${decorators-file}"/>
<page-parsers>
<parser default="true"
class="com.opensymphony.module.sitemesh.parser.FastPageParser"/>
<parser content-type="text/html"
class="com.opensymphony.module.sitemesh.parser.FastPageParser"/>
</page-parsers>
<decorator-mappers>
<mapper class="com.opensymphony.module.sitemesh.mapper.ConfigDecoratorMapper">
<param name="config" value="${decorators-file}"/>
</mapper>
</decorator-mappers>
</sitemesh>
view raw gistfile1.txt hosted with ❤ by GitHub

Create the file /war/WEB-INF/decorators.xml and add
<?xml version="1.0" encoding="UTF-8"?>
<decorators defaultdir="/decorators">
<decorator name="default" page="layout.vm">
<pattern>/*</pattern>
</decorator>
</decorators>
view raw gistfile1.txt hosted with ❤ by GitHub

Create the layout file /war/decorators/layout.vm and add
<html>
<head>
<title>$title</title>
<link href="$base/stylesheets/style.css" rel="stylesheet" type="text/css">
<script src="http://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script>
$head
</head>
<body>
<div id="pageTitle">The title: $title</div>
<hr/>
$body
<div id="footer">
Footer
</div>
</body>
</html>
view raw gistfile1.txt hosted with ❤ by GitHub

Create a velocity file /war/velocity/hello.vm and put the text "Hello World" into it.

Create an empty file /war/WEB-INF/velocity.properties. If you don't do this, you may get an exception saying access denied for reading velocity.properties.

Create a controller called HelloController
public class VideoController {
@RequestMapping(value="/hello", method = RequestMethod.GET)
public ModelAndView sayHello() {
return new ModelAndView("hello");
}
}

Start the server and browse http://localhost:8888/hello and check if you get the decorator content wrapper the Hello World message.


No comments:

Post a Comment