spring-mvc入门(三):映射处理器

  1、简析映射处理器

  在spring mvc中,使用映射处理器可以把web请求映射到正确的处理器上,spring内置了很多映射处理器,而且我们也可以自定义映射处理器。下面的实例展示spring中最常用的两个映射处理器:BeanNameUrlHandlerMapping和SimpleUrlHandlerMapping。在正式开始前有必要了解以下相关要点:

  (1)映射处理器都能把请求传递到处理器执行链接(HandlerExecutionChain)上,并且处理器执行链接必须包含能处理该请求的处理器(实质就是处理器链上动态添加了了此处理器,可以结合filter工作原理理解),而且处理器链接也能包含一系列拦截器。

  (2)上面列举的spring最常用的两种处理器都是继承自AbstractHandlerMapping类,因而它们具备父类的属性。

  2、实例:BeanNameUrlHandlerMapping

  建立springMVC_03_handlerMappingsweb项目,并导入相关jar包。

  步骤一:建立后端控制器MessageController.java,代码如下:

  Java代码

  packagecom.asm; //…省略导入的相关类publicclassMessageControllerimplementsController{ publicModelAndViewhandleRequest(HttpServletRequestarg0,HttpServletResponsearg1)throwsException{ ModelAndViewmav=newModelAndView(“message”); mav.addObject(“message”,”您好!springMVC”); returnmav; } }

  步骤二:配置web.xml,代码如下:

  Xml代码

  “1.0”encoding=”UTF-8″?> <WEB-APPVERSION=“2.4”xmlns=”” xmlns:xsi=”” xsi:schemaLocation=”;”> spmvc <SERVLET-class> org.springframework.web.servlet.DispatcherServlet </SERVLET-class> 1 spmvc *.do

  步骤三:配置spmvc-servlet.xml,代码如下:

  Xml代码

  “1.0”encoding=”UTF-8″?> “” xmlns:xsi=”” xmlns:p=”” xmlns:context=”” xsi:schemaLocation=”;;;”>”viewResolver”class=”org.springframework.web.servlet.view.InternalResourceViewResolver”>

  ”prefix”value=”/WEB-INF/page/”/>

  ”suffix”value=”.jsp”/> “/message.do”class=”com.asm.MessageController”>

  步骤四:在WEB-INF/page目录下建立message.jsp,主要代码如下:

  <body>Message:${message} </body>

  步骤五:启动服务器,输入…/message.do访问测试。

  简析执行过程

  (1)启动服务器后,当我们向服务器发送message.do请求时,首先被在web.xml中配置的前端控制器DispatcherServlet拦截到。

  (2)前端控制器把此请求转交给后端控制器,下面分析转交过程:当在spmvc-servlet.xml中查找能执行message.do请求的映射处理器时,发现没有能处理此请求的映射处理器,这时便使用默认的映射处理器BeanNameUrlHandlerMapping:This is the default implementation used by the DispatcherServlet, along with DefaultAnnotationHandlerMapping (on Java 5 and higher). 我们还需注意:这种后端控制器的bean Name必须以“/”开头,并且要结合DispatcherServlet的映射配置。同时beanName支持通配符配置。比如如果配置: 时,当访问messasge.do时也可以成功访问到MessageController类。

  (3)BeanNameUrlHandlerMapping处理器,会查找在spring容器中是否在名为“message.do”的bean实例。当查找到此实例后,则把此bean作为处理此请求的后端控制器。同时把自身加到映射处理器链上,并向处理器链传递此请求。

  (4)后端控制器进行处理,并返回视图。

  3、实例:SimpleUrlHandlerMapping

  步骤一:建立后端控制器UserContrller.java.代码如下:

  Java代码

  packagecom.asm; //…省略导入的相关类 publicclassUserControllerextendsSimpleFormController{ protectedModelAndViewprocessFormSubmission(HttpServletRequestrequest,HttpServletResponseresponse, Objectcommand,BindExceptionerrors)throwsException{ System.out.println(“调用逻辑层,处理表单”); ModelAndViewmav=newModelAndView(“loginSuc”); returnmav; } }

  步骤二:在spmvc-servlet.xml中增加如下配置:

  Xml代码

  <beanid=”simpleUrlHandlerMapping”class=”org.springframework.web.servlet.handler.SimpleUrlHandlerMapping”> <propertyname=”interceptors”> <list> <refbean=”workTimeInterceptor”/> </list> </property> <propertyname=”mappings”> <props> <propkey=”/op/*/login.do”>userController</prop> </props> </property> </bean> <beanid=”userController”class=”com.asm.UserController”> <propertyname=”commandClass”value=”com.asm.User”/> </bean> <beanid=”workTimeInterceptor” class=”com.asm.LoginTimeInterceptor”> <propertyname=”startTime”value=”6″/> <propertyname=”endTime”value=”18″/> </bean>

  说明:(1)通过前面实例我们可以知道,SimpleController这样的后端控制器必须绑定一个commandClass对象,在这里我们通过配置文件 绑定。

  (2) userController配置说明只要访问是以op开头,中间*可以是任意字符,并以login.do结尾的请求,便能访问到userController 控制器。

  (3)SimpleUrlHandlerMapping是一个更强大的映射处理器,它除了支持上面 的这种配置,还支持Ant风格的路径匹配。另外也可以进行如下形式的配置:

  <propertyname=”mappings”><value>/op/*/login.do=userController</value></property>

  (4)拦截器:为了为某些特殊请求提供特殊功能,spring为映射处理器提供了拦截器支持。它的配置文件很简单:一是把拦截器类纳入spring容器管理,二是在映射处理器引入配置的拦截器bean。

  步骤三:编写拦截器LoginTimeInterceptor.java,主要代码如下:

  Java代码

  packagecom.asm; //…省略导入的相关类 publicclassLoginTimeInterceptorextendsHandlerInterceptorAdapter{ privateintstartTime; privateintendTime; publicvoidsetStartTime(intstartTime){ this.startTime=startTime; } publicvoidsetEndTime(intendTime){ this.endTime=endTime; } publicvoidafterCompletion(HttpServletRequestrequest,HttpServletResponseresponse,Objecthandler, Exceptionex)throwsException{ System.out.println(“执行afterCompletion方法–>03”); super.afterCompletion(request,response,handler,ex); } publicvoidpostHandle(HttpServletRequestrequest,HttpServletResponseresponse,Objecthandler, ModelAndViewmodelAndView)throwsException{ System.out.println(“执行postHandle方法–>02”); super.postHandle(request,response,handler,modelAndView); } publicbooleanpreHandle(HttpServletRequestrequest,HttpServletResponseresponse,Objecthandler) throwsException{ System.out.println(“执行preHandle方法–>01”); Calendarcal=Calendar.getInstance(); inthour=cal.get(Calendar.HOUR_OF_DAY); if(startTime<=hour&&hour<endTime){ returntrue; }else{ response.sendRedirect(“”); returnfalse; } } }

  说明:此拦截器作用:如果用户没有在6-18点登录,则重定向到javaeye站点

  (1)拦截器必须HandlerInterceptorAdapter接口

  (2)preHandle方法在后端控制器执行前被调用,postHandle方法在后端控制器执行后被调用;afterCompletion方法在整个请求处理完成后被调用。

  (3) preHandle方法:返回true,映射处理器执行链将继续执行;当返回false时,DispatcherServlet处理器认为拦截器已经处理完了请求,而不继续执行执行链中的其它拦截器和处理器。它的API文档解释如下:true if the execution chain should proceed with the next interceptor or the handler itself. Else, DispatcherServlet assumes that this interceptor has already dealt with the response itself.

  (4)这三个方法都是相同的参数,Object handler参数可以转化成一个后端控制器对象,比如这里可以转换成UserController对象。

  步骤四:完成其它相关代码的编写User

  java代码

  packagecom.asm;publicclassUser{privateStringusername;privateStringpassword;//省略getter/setter方法}

  WEB-INF/page/loginSuc.jsp,主要代码如下:

  <body>登录成功!欢迎来到后台管理页面 </body>index.jsp代码: <formaction=”/op/luanXie/login.do”method=”post”>用户名:<inputtype=”text”name=”username”><br/>密 码:<inputtype=”password”name=”password”><br/><inputtype=”submit”value=”登录”></form>

  步骤五:访问index.jsp页面,完成测试。

  分析执行过程:为了清晰体会到整个处理器执行过程,我们首先在UserController.java中增加如下代码:

  Java代码

  protectedObjectformBackingObject(HttpServletRequestrequest)throwsException{ System.out.println(“formBackingObject方法执行–>01”); returnsuper.formBackingObject(request); } protectedvoidinitBinder(HttpServletRequestrequest,ServletRequestDataBinderbinder)throwsException{ System.out.println(“initBinder方法执行–>02”); super.initBinder(request,binder); } protectedvoidonBind(HttpServletRequestrequest,Objectcommand)throwsException{ System.out.println(“onBind方法执行–>03”); super.onBind(request,command); } protectedvoidonBindAndValidate(HttpServletRequestrequest,Objectcommand,BindExceptionerrors) throwsException{ System.out.println(“onBindAndValidate方法执行–>04”); super.onBindAndValidate(request,command,errors); }

  (1)当访问…/login.do时,会首先被前端控制器DispatcherServlet拦截到,前端控制器通过查找spmvc-servlet.xml配置文件,并交给后端控制器处理。

  (2)执行后,得到如下打印结果,通过打印结果我们知道它的一个大致执行过程。

  执行preHandle方法–>01

  formBackingObject方法执行–>01

  initBinder方法执行–>02

  onBind方法执行–>03

  onBindAndValidate方法执行–>04

  调用逻辑层,处理表单

  Admin—-123456

  执行postHandle方法–>02

  执行afterCompletion方法–>03

  相关链接:

  Spring-MVC入门(一):入门实例

  Spring-MVC入门(二):后端控制器

一直开到梦的尽头。你曾经说,

spring-mvc入门(三):映射处理器

相关文章:

你感兴趣的文章:

标签云: