Está en la página 1de 32

Spring MVC

Exercise 1: Build and run "springMVCskeleton" sample application


Acknowledgment: This exercise is based on the "Basic Spring Web MVC Example" tutorial from memestorm.com. Heres a simple project, which doesnt use all of Springs features, but serves as a good helloworld-like sample application. When youre putting together a simple web application, you need a few essentials:

A dispatcher servlet, which will intercept incoming requests. A configuration that instructs the web container to route requests to the dispatcher servlet (ie. a servlet mapping) Controllers (the C in MVC) that can perform the business logic and route to particular views (the V) perhaps conveying information models (the M). A way for the dispatcher servlet to know which URLs to map to which controllers called a url mapping A way to determine, when a controller has done its job, how to get to the view - called a view resolver The simple application here, springMVCskeleton, doesnt have a model at all, has a single controller (DispatchController), and a single view (myview.jsp)

(1.1) Open, build, and run "springMVCskeleton" sample JSP application


0. Start NetBeans IDE. 1. Open springMVCskeleton NetBeans project.

Select File->Open Project (Ctrl+Shift+O). The Open Project dialog box appears. Browse down to <LAB_UNZIPPED_DIRECTORY>/springmvc/samples directory. o Windows: If you unzipped the 4918_springmvc.zip file under C:\ directory, the directory to which you want to browse down should be C:\springmvc\samples. o Solaris/Linux: If you unzipped the 4918_springmvc.zip file under $HOME directory, the directory to which you want to browse down should be $HOME/springmvc/samples. Select springMVCskeleton. Click Open Project Folder. Observe that the springMVCskeleton project node appears under Projects tab window.

2. Remove unresolved references and add Spring framework library files and commong logging library files to the project.

You probably don't need all the library files in this project. But for the sake of simplicity of the project, you are adding every library file to the project.

Right click spingMVCskeleton project and select Properties. Observe that Project Properties dialog box appears. Select Libraries under Categories on the left. Remove all broken references on the left by selecting them all and select Remove on the right. Browse down to <LAB_UNZIPPED_DIRECTORY>/springmvc/lib/Springframework-1.2.9 directory. Select all the files and click Open button. Browse down to <LAB_UNZIPPED_DIRECTORY>/springmvc/lib/dom4j1.6.1 directory. Select all the files and click Open button. Browse down to <LAB_UNZIPPED_DIRECTORY>/springmvc/lib/logging-log4j-1.2.14 directory. Select all the files and click Open button. Browse down to <LAB_UNZIPPED_DIRECTORY>/springmvc/lib/struts1.3.8 directory. Select all the files and click Open button. Browse down to <LAB_UNZIPPED_DIRECTORY>/springmvc/lib/jstl directory. Select all the files and click Open button. Click OK button of the Project Properties dialog box to close it.

3. Build and run springMVCskeleton project.

Right-click springMVCskeleton project and select Run Project. Observe the output displayed in the Output window. (Figure-1.15below) Click this link.

Figure-1.15: Result is displayed

Observe the URL is http://localhost:8084/springMVCskeleton/send/actionName.

Figure-1.16: Result is displayed

(1.2) Studt the configuration files


1. web.xml The configuration in the web.xml specifies the following - Create the servlet for me, call it dispatch, and map all incoming URLs that start with send to the dispatch servlet. So for example, a URL such as http://.../skeleton1/send/foobar would activate the dispatch servlet. <?xml version="1.0" encoding="UTF-8"?> <web-app id="WebApp_ID" version="2.4" xmlns="http://java.sun.com/xml/ns/j2ee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/webapp_2_4.xsd"> <display-name>foo</display-name> <context-param> <param-name>log4jConfigLocation</param-name> <param-value>/WEB-INF/log4j.properties</param-value> </context-param> <context-param> <param-name>log4jRefreshInterval</param-name> <param-value>1000</param-value> </context-param> <listener> <listener-class> org.springframework.web.util.Log4jConfigListener </listener-class> </listener> <listener> <listener-class> org.springframework.web.context.ContextLoaderListener </listener-class> </listener> <servlet> <servlet-name>dispatch</servlet-name> <servlet-class>org.springframework.web.servlet.DispatcherServlet</servletclass> <load-on-startup>1</load-on-startup> </servlet>

<servlet-mapping> <servlet-name>dispatch</servlet-name> <url-pattern>/send/*</url-pattern> </servlet-mapping> <welcome-file-list> <welcome-file>index.jsp</welcome-file> </welcome-file-list> </web-app> 2. dispatch-servlet.xml The rest of the configuration is done in the Spring MVC application configuration file. Spring automatically looks for it using the name of the servlet as a hint. Since our servlet is called dispatch, it looks for a file called dispatch-servlet.xml in your WEB-INF directory. This configuration file will have three bits to it: the controller(s), the url mapping and the view resolver. <?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="urlMapping" class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping"> <property name="mappings"> <props> <prop key="/actionNa*">dispatchController</prop> </props> </property> </bean> <bean id="dispatchController" class="com.memestorm.web.DispatchController"> </bean> <bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver"> <property name="prefix"> <value>/WEB-INF/views/</value> </property> <property name="suffix"> <value>.jsp</value> </property> </bean> </beans> 2. applicationContext.xml <?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN" "http://www.springframework.org/dtd/spring-beans.dtd"> <!-- A simple root application context. See dispatch-servlet.xml for the

- Web context. --> <beans> <bean id="a" class="com.memestorm.A"/> <bean id="b" class="com.memestorm.B"> <property name="a" ref="a"/> </bean> </beans>

(1.3) Control flow


1. index.jsp is accessed <!doctype html public "-//w3c//dtd html 4.0 transitional//en"> <html> <head> <title>Spring Skeleton</title> </head> <body> Try accessing the controller by going to <a href="send/actionName">this link</a>. </body> </html> When you click the link in the index.jsp, the control goes to send/actionName, which will be handled by the DispatchServlet of the Spring MVC framework. 2. The actionName() method of the DispatchController class is now called to handle the request according to the configuration in the dispatch-servlet.xml. package com.memestorm.web; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import import import import import org.apache.commons.logging.Log; org.apache.commons.logging.LogFactory; org.springframework.web.context.support.WebApplicationContextUtils; org.springframework.web.servlet.ModelAndView; org.springframework.web.servlet.mvc.multiaction.MultiActionController;

import com.memestorm.B; public class DispatchController extends MultiActionController { public ModelAndView actionName(HttpServletRequest request, HttpServletResponse response) throws Exception { Log log = LogFactory.getLog(this.getClass()); log.info("Controller calling Earth. Come in Earth."); String msg = ((B) (WebApplicationContextUtils .getWebApplicationContext(getServletContext()).getBean("b"))) .getA().foo(); ModelAndView mav = new ModelAndView("myview"); mav.addObject("message", msg);

} }

return mav;

DispatchController.java The actionName() method selects myview as the View to display. It also creates model object in which it added message. The viewResolver selects /WEB-INF/views/myview.jsp as the view to display based on the configuration below. <bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver"> <property name="prefix"> <value>/WEB-INF/views/</value> </property> <property name="suffix"> <value>.jsp</value> </property> </bean> Display the context senstive Javadoc on MultiActionController.

Trouble-shooting: If you don't see the Javadoc as shown above, you have not properly configured the Javadoc of the Spring framework to the NetBeans. Please see here for instruction on how to configure Spring framework Javadoc to the NetBeans. 3. The /WEB-INF/views/myview.jsp is displayed.

<%@ page language="java" contentType="text/html; charset=ISO-8859-1" pageEncoding="ISO-8859-1"%> <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"> <html> <head> <meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1"> <title>Welcome!</title> </head> <body> Hello, you're in myview.jsp! <br /> The controller sent me some data, here it is: <b> <%=request.getAttribute("message") %> </b> </body> </html> Note that it retrieves the value of the message attribute in the request scope and displays it.

Summary
In this exercise, you learned how a controller is selected based on mapping configuration. You also learned how the controller selects a view.

return to the top

Exercise 2: Build and run "springMVCskeleton2" sample application


The "springMVCskeleton2" sample application is a slightly modified version of the springMVCskeleton application. It uses the 2nd controller.

(2.1) Open, build, and run "springMVCskeleton2" sample JSP application


1. Open springMVCskeleton2 NetBeans project.

Select File->Open Project (Ctrl+Shift+O). The Open Project dialog box appears. Browse down to <LAB_UNZIPPED_DIRECTORY>/springmvc/samples directory. Select springMVCskeleton2. Click Open Project Folder. The springMVCskeleton2 project node appears under Projects tab window.

2. Resolve a reference problem as described above. 3. Build and run springMVCskeleton2 project.

Right-click project node and select Run Project. The browser gets displayed. Clicdk this link of the 2nd line.

Note that it is accessing http://localhost:8084/springMVCskeleton2/send/actionName2.

(2.2) Study the configuration files


1. dispatch-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="urlMapping" class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping"> <property name="mappings"> <props> <prop key="/actionName2">dispatchController2</prop> <prop key="/*">dispatchController</prop> </props> </property> </bean> <bean id="dispatchController" class="com.memestorm.web.DispatchController"> </bean>

<bean id="dispatchController2" class="com.memestorm.web.DispatchController2"> </bean> <bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver"> <property name="prefix"> <value>/WEB-INF/views/</value> </property> <property name="suffix"> <value>.jsp</value> </property> </bean> </beans> 2. web.xml <?xml version="1.0" encoding="UTF-8"?> <web-app id="WebApp_ID" version="2.4" xmlns="http://java.sun.com/xml/ns/j2ee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd"> <display-name>foo</display-name> <context-param> <param-name>log4jConfigLocation</param-name> <param-value>/WEB-INF/log4j.properties</param-value> </context-param> <context-param> <param-name>log4jRefreshInterval</param-name> <param-value>1000</param-value> </context-param> <listener> <listener-class> org.springframework.web.util.Log4jConfigListener </listener-class> </listener> <listener> <listener-class> org.springframework.web.context.ContextLoaderListener </listener-class> </listener> <servlet> <servlet-name>dispatch</servlet-name> <servlet-class> org.springframework.web.servlet.DispatcherServlet </servlet-class> <load-on-startup>1</load-on-startup> </servlet> <servlet-mapping> <servlet-name>dispatch</servlet-name>

<url-pattern>/send/*</url-pattern> </servlet-mapping> <servlet-mapping> <servlet-name>dispatch</servlet-name> <url-pattern>/send2/*</url-pattern> </servlet-mapping> <welcome-file-list> <welcome-file>index.jsp</welcome-file> </welcome-file-list> </web-app>

(2.3) Control flow


1. index.jsp is displayed. Welcome. Try accessing the 1st controller by going to <a href="send/actionName">this link</a>. <p> Try accessing the 2nd controller by going to <a href="send/actionName2">this link</a>. When the link for send/actionName2 is clicked, the displatchController2 is used to handle the request according to the configuration below. <bean id="urlMapping" class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping"> <property name="mappings"> <props> <prop key="/actionName2">dispatchController2</prop> <prop key="/*">dispatchController</prop> </props> </property> </bean> <bean id="dispatchController" class="com.memestorm.web.DispatchController"> </bean> <bean id="dispatchController2" class="com.memestorm.web.DispatchController2"> </bean> 2. The actionName2() method of the com.memestorm.web.DispatchController2 class is invoked. package com.memestorm.web; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import import import import import org.apache.commons.logging.Log; org.apache.commons.logging.LogFactory; org.springframework.web.context.support.WebApplicationContextUtils; org.springframework.web.servlet.ModelAndView; org.springframework.web.servlet.mvc.multiaction.MultiActionController;

import com.memestorm.B; public class DispatchController2 extends MultiActionController { public ModelAndView actionName2(HttpServletRequest request, HttpServletResponse response) throws Exception { Log log = LogFactory.getLog(this.getClass()); log.info("Controller calling Earth. Come in Earth."); String msg = ((B) (WebApplicationContextUtils .getWebApplicationContext(getServletContext()).getBean("b"))) .getA().foo(); ModelAndView mav = new ModelAndView("myview2"); mav.addObject("message2", msg); return mav;

} }

The actionName2() method selects myview2 as the view to display. The viewResolver will select /WEB-INF/views/myview2.jsp as the page to display accoring to the configuration below. <bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver"> <property name="prefix"> <value>/WEB-INF/views/</value> </property> <property name="suffix"> <value>.jsp</value> </property> </bean> 3. myview2.jsp is displayed <%@ page language="java" contentType="text/html; charset=ISO-8859-1" pageEncoding="ISO-8859-1"%> <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"> <html> <head> <meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1"> <title>Welcome!</title> </head> <body> Hello, you're in myview2.jsp! <br /> The controller sent me some data, here it is: <b> <%=request.getAttribute("message2") %> </b> </body> </html>

Summary
In this exercise, you learned how to use two different controllers.

return to the top

Exercise 3: Build and run "springMVCbanking" sample application


Acknowledgment: This exercise is based on the "Spring Series, Part 3: Swing into Spring MVC" tutorial written by Naveen Balani.

(3.1) Open, build, and run "springMVCbanking" sample JSP application

1. Open springMVCbanking NetBeans project.

Select File->Open Project (Ctrl+Shift+O). The Open Project dialog box appears. Browse down to <LAB_UNZIPPED_DIRECTORY>/springmvc/samples directory. Select springMVCbanking. Click Open Project Folder. The springMVCbanking project node appears under Projects tab window.

2. Resolve a reference problem as described above. 3. Build and run springMVCbanking project.

Right-click project and select Run Project. Observe that the login page is displayed. For User id field, enter admin. For Password field, enter password. Click login button.

Observe that the Account Details page is displayed.

(3.2) Study the configuration files


1. web.xml <?xml version="1.0" encoding="ISO-8859-1"?> <!DOCTYPE web-app PUBLIC "-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN" "http://java.sun.com/dtd/web-app_2_3.dtd"> <web-app> <context-param> <param-name>contextConfigLocation</param-name> <param-value>/WEB-INF/sampleBanking-services.xml</param-value> </context-param> <servlet> <servlet-name>context</servlet-name> <servlet-class> org.springframework.web.context.ContextLoaderServlet </servlet-class> <load-on-startup>1</load-on-startup> </servlet> <servlet> <servlet-name>sampleBankingServlet</servlet-name> <servlet-class> org.springframework.web.servlet.DispatcherServlet </servlet-class> <load-on-startup>2</load-on-startup> </servlet> <servlet-mapping> <servlet-name>sampleBankingServlet</servlet-name> <url-pattern>*.html</url-pattern> </servlet-mapping> <welcome-file-list> <welcome-file>index.jsp</welcome-file> </welcome-file-list> <taglib>

<taglib-uri>/spring</taglib-uri> <taglib-location>/WEB-INF/spring.tld</taglib-location> </taglib> </web-app> 2. sampleBankingServlet-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="simpleUrlMapping" class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping"> <property name="mappings"> <props> <prop key="/login.html">loginBankController</prop> </props> </property> </bean> <bean id="loginBankController" class="springexample.contoller.LoginBankController"> <property name="sessionForm"> <value>true</value> </property> <property name="commandName"> <value>loginCommand</value> </property> <property name="commandClass"> <value>springexample.commands.LoginCommand</value> </property> <property name="authenticationService"> <ref bean="authenticationService" /> </property> <property name="accountServices"> <ref bean="accountServices" /> </property> <property name="formView"> <value>login</value> </property> <property name="successView"> <value>accountdetail</value> </property> </bean> <bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver"> <property name="viewClass"> <value>org.springframework.web.servlet.view.JstlView</value> </property> <property name="prefix"> <value>/jsp/</value>

</property> <property name="suffix"> <value>.jsp</value> </property> </bean> </beans> 3. simpleBanking-services.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="accountServices" class="springexample.services.AccountServices"> </bean> <bean id="authenticationService" class="springexample.services.AuthenticationService"> </bean> </beans>

(3.3) Control flow


1. index.jsp is displayed. <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd"> <html> <head> <meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1"> <title>Insert title here</title> </head> <body> <jsp:forward page="login.html" /> </body> </html> index.jsp The control is forwarded to login.html, which will be handled by DispatcherServlet. Because of the following mapping configuration, it will be handled, it will be handled by the loginBankController. <bean id="simpleUrlMapping" class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping"> <property name="mappings"> <props> <prop key="/login.html">loginBankController</prop> </props> </property> </bean>

2. loginBankController's onSubmit() method is called. package springexample.contoller; import org.springframework.web.servlet.ModelAndView; import org.springframework.web.servlet.mvc.SimpleFormController; import import import import springexample.commands.AccountDetail; springexample.commands.LoginCommand; springexample.services.AccountServices; springexample.services.AuthenticationService;

/** * @author naveenb */ public class LoginBankController extends SimpleFormController { public LoginBankController(){ } protected ModelAndView onSubmit(Object command) throws Exception{ LoginCommand loginCommand = (LoginCommand) command; authenticationService.authenticate(loginCommand); AccountDetail accountdetail = accountServices.getAccountSummary(loginCommand.getUserId()); return new ModelAndView(getSuccessView(),"accountdetail",accountdetail); } private AuthenticationService authenticationService; private AccountServices accountServices; /** * @return Returns the accountServices. */ public AccountServices getAccountServices() { return accountServices; } /** * @param accountServices The accountServices to set. */ public void setAccountServices(AccountServices accountServices) { this.accountServices = accountServices; } /** * @return Returns the authenticationService. */ public AuthenticationService getAuthenticationService() { return authenticationService; } /** * @param authenticationService The authenticationService to set. */ public void setAuthenticationService( AuthenticationService authenticationService) {

} }

this.authenticationService = authenticationService;

Do the context senstive Javadoc on the SimpleFormController class.

Based on the viewResolver configuration, the controller will select /jsp/accountdetail.jsp as the next view page. <bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver"> <property name="viewClass"> <value>org.springframework.web.servlet.view.JstlView</value> </property> <property name="prefix"> <value>/jsp/</value> </property> <property name="suffix"> <value>.jsp</value> </property> </bean> 3. /jsp/accountdetail.jsp is displayed. <%@ taglib prefix="c" uri="http://java.sun.com/jstl/core"%> <%@ taglib prefix="spring" uri="/spring"%> <html> <head> <title>Login to Spring Example Account Banking</title> </head> <body> <h1> Account Details </h1> <p> <form method="post"> <spring:bind path="accountdetail"> <c:forEach items="${status.errorMessage}" var="errorMessage"> <font color="red"> <c:out value="${errorMessage}" /> <br> </font> </c:forEach> </spring:bind> <table width="95%" bgcolor="f8f8ff" border="0" cellspacing="0" cellpadding="5"> Following are the list of your accounts and its details. <c:forEach items="${accountdetail.accountsList}" var="accountsList"> <tr> <td alignment="right" width="20%"> Account Name: <c:out value="${accountsList.accountName}" /> </td> <td alignment="right" width="20%"> Account Type: <c:out value="${accountsList.accountType}" /> </td> <td alignment="left" width="20%"> Account Number:

<c:out value="${accountsList.accountNumber}" /> </td> <td alignment="right" width="20%"> Account Balance: <c:out value="${accountsList.accountbalance}" /> </td> <td width="60%"> </tr> <tr> </tr> </c:forEach> </table> <br /> <a href="/springMVCbanking/login.html">logout</a> </body> </html>

Summary
In this exercise, you have built and run a ready-to-build-and-run "SpringInjectionNaming" sample application.

return to the top

Exercise 4: Build and run "JumpIntoSpringMVC" sample application


Acknowledgment: This exercise is based on the sample applications provided by Spring MVC abd Wev Flow book written by Seth Ladd, Darren Davison, Steven Devijver, and Colin Yeates. The book is highly recommended.

(4.1) Open, build, and run "JumpIntoSpringMVC" sample JSP application

1. Open JumpIntoSpringMVC NetBeans project.

Select File->Open Project (Ctrl+Shift+O). The Open Project dialog box appears. Browse down to <LAB_UNZIPPED_DIRECTORY>/springmvc/samples directory. Select JumpIntoSpringMVC. Click Open Project Folder. The JumpIntoSpringMVC project node appears under Projects tab window.

2. Resolve a reference problem as described above. 3. Build and run JumpIntoSpringMVC project.

Right-click project and select Run Project. Observe the result is displayed in the Output window.

(4.2) Study the configuration files


1. web.xml <?xml version="1.0" encoding="UTF-8"?> <web-app version="2.4" xmlns="http://java.sun.com/xml/ns/j2ee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd"> <display-name>JumpIntoSpringMVC</display-name> <listener> <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>detectAllViewResolvers</param-name> <param-value>false</param-value> </init-param> </servlet> <servlet-mapping> <servlet-name>spring</servlet-name>

<url-pattern>/app/*</url-pattern> </servlet-mapping> <welcome-file-list> <welcome-file>index.html</welcome-file> <welcome-file>index.jsp</welcome-file> </welcome-file-list> </web-app> 2. spring-servlet.xml <?xml version="1.0"?> <!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN" "http://www.springframework.org/dtd/spring-beans.dtd"> <beans> <bean id="messageSource" class="org.springframework.context.support.ResourceBundleMessageSource"> <property name="basenames"> <list> <value>messages</value> </list> </property> </bean> <bean id="handlerMapping" class="org.springframework.web.servlet.handler.BeanNameUrlHandlerMapping"> <property name="interceptors"> <list> <bean class="com.apress.expertspringmvc.flight.web.DateInsertionInterceptor" /> </list> </property> </bean> <bean name="/home" class="com.apress.expertspringmvc.flight.web.HomeController"> <property name="flightService" ref="flightService" /> </bean> <bean name="/search" class="com.apress.expertspringmvc.flight.web.SearchFlightsController"> <property name="flightService" ref="flightService" /> </bean> <bean name="/cancelAccount" singleton="false" class="com.apress.expertspringmvc.flight.web.CancelAccountController"> <property name="accountService" ref="accountService" /> </bean> <bean name="/account/*" class="com.apress.expertspringmvc.flight.web.ViewAccountController"> <property name="accountService" ref="accountService" /> </bean>

<bean name="/createAccount" class="com.apress.expertspringmvc.flight.web.CreateAccountWizardController"> <property name="accountService" ref="accountService" /> </bean> <bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver"> <property name="prefix" value="/WEB-INF/jsp/" /> <property name="suffix" value=".jsp"/> </bean> </beans> 3. applicationContext.xml <?xml version="1.0"?> <!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN" "http://www.springframework.org/dtd/spring-beans.dtd"> <beans> <bean id="flightService" class="com.apress.expertspringmvc.flight.service.DummyFlightService" /> <bean id="accountService" class="com.apress.expertspringmvc.flight.service.AccountServiceImpl" /> </beans>

(4.3) Control flow


1. jsp/home.jsp is accessed <?xml version="1.0" encoding="ISO-8859-1" ?> <%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %> <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head> <meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1" /> <title>Flight Booking Service</title> </head> <body> <h1>Welcome to the Flight Booking Service</h1> <p>We have the following specials now:</p> <ul> <c:forEach items="${specials}" var="special"> <li>${special.departFrom.name} - ${special.arriveAt.name} from $${special.cost}</li> </c:forEach> </ul> <p><a href="search">Search for a flight.</a></p>

</body> </html> 2. com.apress.expertspringmvc.flight.web.SearchFlightsController handles the request package com.apress.expertspringmvc.flight.web; import java.text.SimpleDateFormat; import java.util.Date; import javax.servlet.http.HttpServletRequest; import import import import org.springframework.beans.propertyeditors.CustomDateEditor; org.springframework.web.bind.ServletRequestDataBinder; org.springframework.web.servlet.ModelAndView; org.springframework.web.servlet.mvc.SimpleFormController;

import com.apress.expertspringmvc.flight.domain.FlightSearchCriteria; import com.apress.expertspringmvc.flight.service.FlightService; public class SearchFlightsController extends SimpleFormController { private FlightService flights; public SearchFlightsController() { setCommandName("flightSearchCriteria"); setCommandClass(FlightSearchCriteria.class); setFormView("beginSearch"); setSuccessView("listFlights"); } public void setFlightService(FlightService flights) { this.flights = flights; } @Override protected void initBinder(HttpServletRequest req, ServletRequestDataBinder binder) throws Exception { binder.registerCustomEditor(Date.class, new CustomDateEditor( new SimpleDateFormat("yyyy-MM-dd HH"), true)); } @Override protected ModelAndView onSubmit(Object command) throws Exception { FlightSearchCriteria search = (FlightSearchCriteria) command; ModelAndView mav = new ModelAndView(getSuccessView()); mav.addObject("flights", flights.findFlights(search)); mav.addObject("flightSearchCriteria", search); return mav; } } 3. /jsp/listFlights.jsp is displayed <?xml version="1.0" encoding="ISO-8859-1" ?> <%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %> <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"

"http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head> <meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1" /> <title>List Flights</title> </head> <body> <h1>List Flights</h1> <p> You searched for flights leaving ${flightSearchCriteria.departFrom} on or about ${flightSearchCriteria.departOn}, heading to ${flightSearchCriteria.arriveAt}, returning or about ${flightSearchCriteria.returnOn}. </p> <table> <thead> <tr> <th>Number of Legs</th> <th>Total Travel Time</th> <th>Total Cost</th> </tr> </thead> <tbody> <c:forEach items="${flights}" var="flight"> <tr> <td>${flight.numberOfLegs}</td> <td>${flight.totalTravelTimeHours}</td> <td>$${flight.totalCost}</td> </tr> </c:forEach> </tbody> </table> </body> </html>

on

Summary
In this exercise, you have built and run a ready-to-build-and-run "JumpIntoSpringMVC" sample application.

return to the top

Exercise 5: Build and run "ExpertSpringMVC" sample application


Acknowledgment: This exercise is based on the sample applications provided by Spring MVC abd Wev Flow book written by Seth Ladd, Darren Davison, Steven Devijver, and Colin Yeates. The book is highly recommended.

(5.1) Open, build, and run "ExpertSpringMVC" sample JSP application

1. Open ExpertSpringMVC NetBeans project.

Select File->Open Project (Ctrl+Shift+O). The Open Project dialog box appears. Browse down to <LAB_UNZIPPED_DIRECTORY>/springmvc/samples directory. Select ExpertSpringMVC. Click Open Project Folder. The ExpertSpringMVC project node appears under Projects tab window.

2. Remove broken references and add libaries. You probably don't need all the library files in this project. But for the sake of simplicity of the project, you are adding every library file to the project.

Right click spingMVCskeleton project and select Properties. Observe that Project Properties dialog box appears. Select Libraries under Categories on the left. Remove all broken references on the left by selecting them all and select Remove on the right. Browse down to <LAB_UNZIPPED_DIRECTORY>/springmvc/lib/Springframework-1.2.9 directory. Select all the files and click Open button. Browse down to <LAB_UNZIPPED_DIRECTORY>/springmvc/lib/dom4j1.6.1 directory. Select all the files and click Open button. Browse down to <LAB_UNZIPPED_DIRECTORY>/springmvc/lib/logging-log4j-1.2.14 directory. Select all the files and click Open button. Browse down to <LAB_UNZIPPED_DIRECTORY>/springmvc/lib/struts1.3.8 directory. Select all the files and click Open button. Browse down to <LAB_UNZIPPED_DIRECTORY>/springmvc/lib/jstl directory. Select all the files and click Open button. Browse down to <LAB_UNZIPPED_DIRECTORY>/springmvc/lib2 directory. Select all the files and click Open button. Click OK button of the Project Properties dialog box to close it.

3. Build and run ExpertSpringMVC project.

Right-click project and select Run Project. Observe the result is displayed in the Output window.

(5.2) Study the configuration files


1. spring-servlet.xml <?xml version="1.0"?> <!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN" "http://www.springframework.org/dtd/spring-beans.dtd"> <beans> <bean name="/home" class="com.apress.expertspringmvc.flight.web.HomeController"> <property name="flightService" ref="flightService" /> </bean> <bean name="/search" class="com.apress.expertspringmvc.flight.web.SearchFlightsController"> <property name="flightService" ref="flightService" /> </bean> <!-<bean id="mixedResolver" class="org.springframework.web.servlet.view.ResourceBundleViewResolver"> <property name="order" value="1"/> <property name="basename" value="views"/> </bean> --> <bean id="velocityResolver" class="org.springframework.web.servlet.view.velocity.VelocityViewResolver"> <property name="prefix" value="" /> <property name="suffix" value=".vm"/> <property name="exposeSpringMacroHelpers" value="true"/> <property name="requestContextAttribute" value="rc"/> <property name="dateToolAttribute" value="date"/> <property name="numberToolAttribute" value="number"/> </bean> <!-<bean id="freemarkerResolver" class="org.springframework.web.servlet.view.freemarker.FreeMarkerViewResolver"> <property name="prefix" value="" /> <property name="suffix" value=".ftl"/> <property name="exposeSpringMacroHelpers" value="true"/> </bean> --> <!-<bean id="jspViewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver"> <property name="prefix" value="/WEB-INF/jsp/" /> <property name="suffix" value=".jsp"/> </bean>

--> <bean id="tilesConfigurer" class="org.springframework.web.servlet.view.tiles.TilesConfigurer"> <property name="definitions"> <list> <value>/WEB-INF/tiles/defs-main.xml</value> </list> </property> </bean> <bean id="velocityConfigurer" class="org.springframework.web.servlet.view.velocity.VelocityConfigurer"> <property name="resourceLoaderPath" value="/WEB-INF/velocity"/> </bean> <bean id="freemarkerConfigurer" class="org.springframework.web.servlet.view.freemarker.FreeMarkerConfigurer"> <property name="templateLoaderPath" value="/WEB-INF/freemarker"/> </bean> <bean id="themeResolver" class="org.springframework.web.servlet.theme.FixedThemeResolver"> <property name="defaultThemeName" value="summer"/> </bean> <bean id="themeSource" class="org.springframework.ui.context.support.ResourceBundleThemeSource"> <property name="basenamePrefix" value="com.apress.expertspringmvc.themes."/> </bean> </beans>

!-- This xml contain all entry of bean classes for urlMapping and entry for tiles,validation files as well as interceptor --> <bean id="viewResolver"

class="org.springframework.web.servlet.view.InternalResourceViewResolve r"> <property name="viewClass" value="org.springframework.web.servlet.view.tiles.TilesJstlView" /> </bean> <bean id="tilesConfigurer"

class="org.springframework.web.servlet.view.tiles.TilesConfigurer"> <property name="definitions"> <list> <value>

/WEB-INF/resources/template-tiles-defs.xml </value> <value> /WEB-INF/resources/provider-profiletiles-defs.xml </value> </list> </property> </bean> <bean id="multipartResolver"

class="org.springframework.web.multipart.commons.CommonsMultipartResolv er" /> <!-- bean id="messageSource" class="org.springframework.context.support.ResourceBundleMessageSource"> <property name="basename"> <value>message_en_US</value> </property> </bean--> <bean id="localeResolver"

class="org.springframework.web.servlet.i18n.AcceptHeaderLocaleResolver" /> <bean id="urlMapping"

class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping"> <property name="interceptors"> <list> <ref bean="securityInterceptor"/> <!-- this shold always be the first interceptor --> </list> </property> <property name="mappings"> <props> <!--Common --> <prop key="/home.htm">homeController</prop> <prop key="/provider/co.htm">centralOfficeController</prop> </props> </property> </bean> <!-- HCASecurityInterceptor --> <bean id="securityInterceptor" class="com.pnc.tsc.hca.web.common.HCASecurityInterceptor">

<property name="securityDelegate" ref="securityDelegate" /> </bean> <!-- HomeController --> <bean id="homeController" class="com.pnc.tsc.hca.web.common.HomeController"> <property name="homeView" value="hca.home" /> </bean> <!-- Central Office Controller --> <bean id="centralOfficeController" class="com.pnc.tsc.hca.web.tp.provider.ProviderCenrtalOfficeController"> <property name="view" value="hca.provider.co.office.view" /> </bean> <bean id="securityDelegate" class="com.pnc.tsc.hca.web.common.SecurityDelegate" > <property name="securityService" ref="securityService"/> </bean> <!-- bean id="securityService" class="org.springframework.ejb.access.LocalStatelessSessionProxyF actoryBean" lazy-init="true"> <property name="jndiName" value="java:comp/env/ejb/SecuritySessionFacade"/> <property name="businessInterface" value="com.pnc.tsc.hca.service.SecurityService"/> </bean--> </beans>

También podría gustarte