I use Velocity a lot in my projects as I dont need
over-engineered JSPs in my simple templates.
I use the View Layout tools to simplefy even further.
And by editing a couple of xml files, spring uses its full potential.
These libraries need to be included:
and their dependencies e.g.
And my own
but more about that later.
First here is sections of my web.xml. Some bits are just standard spring mvc setup.
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>/WEB-INF/spring/applicationContext.xml</param-value>
</context-param>
<listener>
<description>ServletContextListener</description>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
<servlet>
<servlet-name>spring</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>/WEB-INF/spring/spring-servlet.xml</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>spring</servlet-name>
<url-pattern>*.html</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>spring</servlet-name>
<url-pattern>*.do</url-pattern>
</servlet-mapping>
<!--
These two mappings is a fudge due to silly web-app specs.
It avoids having jsp forward to html files
-->
<servlet-mapping>
<servlet-name>spring</servlet-name>
<url-pattern>/index.html</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>spring</servlet-name>
<url-pattern>/contact/index.html</url-pattern>
</servlet-mapping>
<welcome-file-list>
<welcome-file>index.html</welcome-file>
</welcome-file-list>
<!-- My own error pages, not a requirement -->
<error-page>
<error-code>404</error-code>
<location>/missing.html</location>
</error-page>
<error-page>
<error-code>403</error-code>
<location>/access.html</location>
</error-page>
<error-page>
<error-code>500</error-code>
<location>/error.html</location>
</error-page>
And here is my spring-servlet.xml
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN" "http://www.springframework.org/dtd/spring-beans.dtd">
<beans>
<bean id="velocityConfig" class="org.springframework.web.servlet.view.velocity.VelocityConfigurer">
<property name="resourceLoaderPath" value="/"/>
<property name="configLocation" value="/WEB-INF/velocity/velocity.properties"/>
</bean>
<bean id="viewResolvers" class="com.flurdy.grid.mvc.view.VelocityLayoutViewResolver">
<property name="layoutUrl" value="WEB-INF/templates/layout/grid.vm"/>
<property name="toolboxConfigLocation" value="/WEB-INF/velocity/toolbox.xml"/>
<property name="prefix" value="/WEB-INF/templates/"/>
<property name="suffix" value=".vm"/>
<property name="exposeSpringMacroHelpers" value="true"/>
</bean>
<bean id="internalResolver" class="org.springframework.web.servlet.mvc.multiaction.InternalPathMethodNameResolver">
<property name="suffix" value="Handler"/>
</bean>
<bean id="messageSource" class="org.springframework.context.support.ResourceBundleMessageSource">
<property name="basenames">
<list>
<value>text</value>
</list>
</property>
</bean>
<bean id="handler" class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping">
<property name="mappings">
<props>
<prop key="/**/*.html">viewController</prop>
<prop key="/**/*.do">viewController</prop>
</props>
</property>
</bean>
<bean id="viewController" class="org.springframework.web.servlet.mvc.multiaction.MultiActionController">
<property name="methodNameResolver" ref="internalResolver"/>
<property name="delegate" ref="viewDelegate"/>
</bean>
<bean id="viewDelegate" class="some.package.ViewDelegate">
<!-- <property name="someinjection" ref="someotherbean"/> -->
</bean>
</beans>
As you see the viewResolvers bean uses my own VelocityLayoutViewResolver. This is due to my set up uses the VelocityLayoutView tools. And spring does not include a resolver for it in its 1.x version. It is however included in the lastest versions. More details here.
Next thing is to create a grid.vm layout template referenced in the viewResolvers bean. I tend to use a specific css based layout, but that will be detailed in another doc sometime.
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
<title>
#springMessage("title")
</title>
<link rel="shortcut icon" href="$request.contextPath/favicon.ico" />
<link type="text/css" rev="StyleSheet" rel="StyleSheet" href="http://flurdy.com/style/grid.css" />
<link type="text/css" rev="StyleSheet" rel="StyleSheet" href="http://flurdy.com/style/ship.css" />
<link type="text/css" rev="StyleSheet" rel="StyleSheet" href="http://flurdy.com/style/cargo.css" />
</head>
<body>
<div id="ship">
<div id="stern" class="grid head">
<span>
#springMessage("titlelong")
</span>
</div>
<div id="port" class="grid side column">
<ul id="menu">
<li><a href="$request.contextPath/index.html">Home</a></li>
## <li><a href="$request.contextPath/contact/">Contact</a></li>
</ul>
</div>
<div id="starboard" class="grid side column">
</div>
<div id="outerhull" class="">
<div id="innerhull" class="grid column middle">
<div id="cargo" class="">
/ <a href="$request.contextPath/">home</a>
$screen_content
</div>
</div>
</div>
<div id="aft" class="grid foot">
</div>
</div>
</body>
</html>
What is of interest is the two #springMessage lines and the $screen_content. The springmessages prints out text from your resource bundles, ie the messageResource in the spring-servlet.xml.
The $screen_content is where your view templates will be inserted. More details here.
Final thing is to include the handler delegate. Here is quick example.
package some.package;
import java.util.*;
import javax.servlet.http.*;
import org.springframework.web.servlet.ModelAndView;
import org.apache.commons.logging.*;
//import org.apache.commons.collections.*;
//import ent.orm.*;
//import mng.face.*;
//import dao.face.*;
//import logic.face.*;
public class ViewDelegate {
private final Log log = LogFactory.getLog(getClass());
public ModelAndView unspecified(
HttpServletRequest req,HttpServletResponse resp ) {
log.info("unspecified");
return indexHandler(req,resp);
}
public ModelAndView indexHandler(
HttpServletRequest req,HttpServletResponse resp ) {
Map model = new HashMap();
return new ModelAndView("front",model);
}
public ModelAndView missingHandler(
HttpServletRequest req,HttpServletResponse resp ) {
log.warn("Page is missing:");
return new ModelAndView("core/missing");
}
public ModelAndView accessHandler(
HttpServletRequest req,HttpServletResponse resp ) {
log.warn("No access");
return new ModelAndView("core/access");
}
public ModelAndView errorHandler(
HttpServletRequest req,HttpServletResponse resp ) {
return new ModelAndView("core/error");
}
}
You will need to create some templates, e.g. front.vm. Which need to go into WEB-INF/templates.
Contact me if there is sections missing or if you have any questions.