springMVC的拦截器

SpringMVC中的Interceptor拦截器也是相当重要和相当有用的,它的主要作用是拦截用户的请求并进行相应的处理。比如通过它来进行权限验证,或者是来判断用户是否登陆,或者是像12306那样子判断当前时间是否是购票时间。

   一、定义Interceptor实现类

   SpringMVC中的Interceptor拦截请求是通过HandlerInterceptor来实现的。在SpringMVC中定义一个Interceptor非常简单,主要有两种方式,第一种方式是要定义的Interceptor类要实现了Spring的HandlerInterceptor 接口,或者是这个类继承实现了HandlerInterceptor接口的类,比如Spring已经提供的实现了HandlerInterceptor接口的抽象类HandlerInterceptorAdapter ;第二种方式是实现Spring的WebRequestInterceptor接口,或者是继承实现了WebRequestInterceptor的类。

   (一)实现HandlerInterceptor接口

   HandlerInterceptor接口中定义了三个方法,我们就是通过这三个方法来对用户的请求进行拦截处理的。

   (1)preHandle(HttpServletRequest request, HttpServletResponse response, Object handle)方法,顾名思义,该方法将在请求处理之前进行调用。SpringMVC中的Interceptor是链式的调用的,在一个应用中或者说是在一个请求中可以同时存在多个Interceptor。每个Interceptor的调用会依据它的声明顺序依次执行,而且最先执行的都是Interceptor中的preHandle方法,所以可以在这个方法中进行一些前置初始化操作或者是对当前请求的一个预处理,也可以在这个方法中进行一些判断来决定请求是否要继续进行下去。该方法的返回值是布尔值Boolean类型的,当它返回为false时,表示请求结束,后续的Interceptor和Controller都不会再执行;当返回值为true时就会继续调用下一个Interceptor的preHandle方法,如果已经是最后一个Interceptor的时候就会是调用当前请求的Controller方法。

   (2)postHandle(HttpServletRequest request, HttpServletResponse response, Object handle, ModelAndView modelAndView)方法,由preHandle方法的解释我们知道这个方法包括后面要说到的afterCompletion方法都只能是在当前所属的Interceptor的preHandle方法的返回值为true时才能被调用。postHandle方法,顾名思义就是在当前请求进行处理之后,也就是Controller方法调用之后执行,但是它会在DispatcherServlet进行视图返回渲染之前被调用,所以我们可以在这个方法中对Controller处理之后的ModelAndView对象进行操作。postHandle方法被调用的方向跟preHandle是相反的,也就是说先声明的Interceptor的postHandle方法反而会后执行,这和Struts2里面的Interceptor的执行过程有点类型。Struts2里面的Interceptor的执行过程也是链式的,只是在Struts2里面需要手动调用ActionInvocation的invoke方法来触发对下一个Interceptor或者是Action的调用,然后每一个Interceptor中在invoke方法调用之前的内容都是按照声明顺序执行的,而invoke方法之后的内容就是反向的。

   (3)afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handle, Exception ex)方法,该方法也是需要当前对应的Interceptor的preHandle方法的返回值为true时才会执行。顾名思义,该方法将在整个请求结束之后,也就是在DispatcherServlet渲染了对应的视图之后执行。这个方法的主要作用是用于进行资源清理工作的。

(二)实现WebRequestInterceptor接口

  WebRequestInterceptor中也定义了三个方法,我们也是通过这三个方法来实现拦截的。这三个方法都传递了同一个参数WebRequest,那么这个WebRequest是什么呢?这个WebRequest是Spring定义的一个接口,它里面的方法定义都基本跟HttpServletRequest一样,在WebRequestInterceptor中对WebRequest进行的所有操作都将同步到HttpServletRequest中,然后在当前请求中一直传递。

   (1)preHandle(WebRequestrequest)方法。该方法将在请求处理之前进行调用,也就是说会在Controller方法调用之前被调用。这个方法跟HandlerInterceptor中的preHandle是不同的,主要区别在于该方法的返回值是void,也就是没有返回值,所以我们一般主要用它来进行资源的准备工作,比如我们在使用Hibernate的时候可以在这个方法中准备一个Hibernate的Session对象,然后利用WebRequest的setAttribute(name, value, scope)把它放到WebRequest的属性中。这里可以说说这个setAttribute方法的第三个参数scope,该参数是一个Integer类型的。在WebRequest的父层接口RequestAttributes中对它定义了三个常量:

   SCOPE_REQUEST:它的值是0,代表只有在request中可以访问。

   SCOPE_SESSION:它的值是1,如果环境允许的话它代表的是一个局部的隔离的session,否则就代表普通的session,并且在该session范围内可以访问。

   SCOPE_GLOBAL_SESSION:它的值是2,如果环境允许的话,它代表的是一个全局共享的session,否则就代表普通的session,并且在该session范围内可以访问。

   (2)postHandle(WebRequestrequest, ModelMap model)方法。该方法将在请求处理之后,也就是在Controller方法调用之后被调用,但是会在视图返回被渲染之前被调用,所以可以在这个方法里面通过改变数据模型ModelMap来改变数据的展示。该方法有两个参数,WebRequest对象是用于传递整个请求数据的,比如在preHandle中准备的数据都可以通过WebRequest来传递和访问;ModelMap就是Controller处理之后返回的Model对象,我们可以通过改变它的属性来改变返回的Model模型。

   (3)afterCompletion(WebRequestrequest, Exception ex)方法。该方法会在整个请求处理完成,也就是在视图返回并被渲染之后执行。所以在该方法中可以进行资源的释放操作。而WebRequest参数就可以把我们在preHandle中准备的资源传递到这里进行释放。Exception参数表示的是当前请求的异常对象,如果在Controller中抛出的异常已经被Spring的异常处理器给处理了的话,那么这个异常对象就是是null。
二、拦截器示例:

MyInterceptor.java

 1 package com.tgb.interceptor;
 2
 3 import java.util.List;
 4
 5 import javax.servlet.http.HttpServletRequest;
 6 import javax.servlet.http.HttpServletResponse;
 7
 8
 9 import org.springframework.web.servlet.HandlerInterceptor;
10 import org.springframework.web.servlet.ModelAndView;
11
12 import com.tgb.entity.Student;
13 /**
14  * 自定义springmvc的拦截器
15 * @ClassName: MyInterceptor
16 * @Description: TODO(这里用一句话描述这个类的作用)
17 * @author 尚晓飞
18 * @date 2014-11-3 上午11:07:07
19 *
20  */
21 public class MyInterceptor implements HandlerInterceptor{
22
23     private List<String> allowsUrl;//可以再xml配置的时候进行赋值
24
25     // afterCompletion()方法在DispatcherServlet完全处理完请求后被调用
26     //afterCompletion():这个方法在DispatcherServlet完全处理完请求后被调用,
27     //可以在该方法中进行一些资源清理的操作。
28     @Override
29     public void afterCompletion(HttpServletRequest arg0,
30             HttpServletResponse arg1, Object arg2, Exception arg3)
31             throws Exception {
32         System.out.println("MyInterceptor.afterCompletion(DispatcherServlet完全处理完请求后被调用)");
33
34
35     }
36
37     //业务处理请求之后被调用(preHandle此方法返回false,该方法不执行)
38     //postHandle():这个方法在业务处理器处理完请求后,被调用。该方法执行是,jsp等视图还没有渲染。
39     //在该方法中对用户请求request进行处理。
40     @Override
41     public void postHandle(HttpServletRequest arg0, HttpServletResponse arg1,
42             Object arg2, ModelAndView arg3) throws Exception {
43         System.out.println("MyInterceptor.postHandle(业务处理请求之后被调用)");
44
45     }
46
47     //业务处理请求之前被调用
48     //preHandle():这个方法在业务处理器处理请求之前被调用,在该方法中对用户请求request进行处理。
49     //如果程序员决定该拦截器对请求进行拦截处理后还要调用其他的拦截器,或者是业务处理器去进行处理,则返回true;
50     //如果程序员决定不需要再调用其他的组件去处理请求,则返回false。
51     @Override
52     public boolean preHandle(HttpServletRequest arg0, HttpServletResponse arg1,
53             Object arg2) throws Exception {
54         String uri=arg0.getRequestURI();
55         String url=arg0.getRequestURL().toString();
56         System.out.println("MyInterceptor.preHandle(业务处理请求之前被调用)");
57         System.out.println("MyInterceptor.preHandle(第一个拦截器:uri)"+uri);
58         System.out.println("MyInterceptor.preHandle(第一个拦截器:url)"+url);
59
60         //进行拦截的地址,可以对url进行重定向
61         //获取session
62         Student student=(Student) arg0.getSession().getAttribute("student");
63         if(student==null){
64             //用户未登录或者正在登录。但拦截器已经过滤了登录url的请求。因此为虽已经登录,但session死亡
65             arg0.getSession().setAttribute("msg", "长时间未操作,请重新登录");
66             //重定向
67             arg1.sendRedirect("/test_ssh/login.jsp");
68             //请求转发
69             //arg0.getRequestDispatcher("/test_ssh/login.jsp").forward(arg0, arg1);
70
71         }
72         return true;
73     }
74
75     public List<String> getAllowsUrl() {
76         return allowsUrl;
77     }
78
79     public void setAllowsUrl(List<String> allowsUrl) {
80         this.allowsUrl = allowsUrl;
81     }
82
83
84
85 }

View Code

拦截器的配置。在配置控制器的xml中配置。spring-mvc.xml

 1 <?xml version="1.0" encoding="UTF-8"?>
 2 <beans xmlns="http://www.springframework.org/schema/beans"
 3     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
 4     xmlns:context="http://www.springframework.org/schema/context"
 5     xmlns:mvc="http://www.springframework.org/schema/mvc"
 6     xsi:schemaLocation="http://www.springframework.org/schema/beans
 7     http://www.springframework.org/schema/beans/spring-beans.xsd
 8     http://www.springframework.org/schema/context
 9     http://www.springframework.org/schema/context/spring-context-3.2.xsd
10     http://www.springframework.org/schema/mvc
11     http://www.springframework.org/schema/mvc/spring-mvc-3.2.xsd">
12
13     <!--此xml是springMvc是启动控制器和视图解析工具的 -->
14
15     <!-- 注解扫描包 pojo处定义@Controller,此配置扫描相应的类包,将有注解的pojo变成一个可以分发http请求的控制器-->
16     <!-- @Controller将pojo变成可以分发http请求的控制器。 -->
17     <!-- @RequestMapping确定不同请求,调用不同控制器中的某个控制器,然后调用某个控制器中的某个方法 -->
18     <!-- 类头定义@RequestMapping是提供初步的请求映射信息(相对于项目部署),方法头定义@RequestMapping(相对于类头部署)是确定请求所要调用的方法。请求规则包含:url,请求参数,请求方法,请求头 -->
19     <context:component-scan base-package="com.tgb.web" />
20
21     <!-- <mvc:annotation-driven /> 是一种简写形式,完全可以手动配置替代这种简写形式,简写形式可以让初学都快速应用默认配置方案。<mvc:annotation-driven />
22             会自动注册DefaultAnnotationHandlerMapping与AnnotationMethodHandlerAdapter 两个bean,是spring MVC为@Controllers分发请求所必须的。
23             并提供了:数据绑定支持,@NumberFormatannotation支持,@DateTimeFormat支持,@Valid支持,读写XML的支持(JAXB),读写JSON的支持(Jackson)。
24            后面,我们处理响应ajax请求时,就使用到了对json的支持。后面,对action写JUnit单元测试时,要从spring IOC容器中取DefaultAnnotationHandlerMapping
25            与AnnotationMethodHandlerAdapter 两个bean,来完成测试,取的时候要知道是<mvc:annotation-driven />这一句注册的这两个bean。-->
26     <mvc:annotation-driven />
27
28
29     <!-- 静态资源(js/image)的访问 -->
30     <mvc:resources location="/js/" mapping="/js/**"/>
31
32
33     <!-- 定义视图解析器 -->
34     <bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver">
35         <property name="prefix" value="/"></property>
36         <property name="suffix" value=".jsp"></property>
37     </bean>
38
39     <!-- 配置springMVC拦截器 。内部可以配置多个拦截器。一个拦截器是一个<mvc:interceptor></mvc:interceptor>节点。执行顺序,根据配置的上下顺序-->
40     <mvc:interceptors>
41         <!-- 第一个拦截器 -->
42         <mvc:interceptor>
43             <!-- 凡是请求路径符合/*/*都被该拦截器拦截 -->
44             <mvc:mapping path="/*/*"/>
45             <!-- 可以指定对某些请求地址不进行拦截 -->
46             <mvc:exclude-mapping path="/student/findAll"/>
47             <!-- 自定义拦截器的java类。 -->
48             <bean class="com.tgb.interceptor.MyInterceptor">
49                 <property name="allowsUrl"><!-- 自定义拦截器类中的一个list属性。以下为该list属性赋值 。此处做判断,表示不拦截的url-->
50                     <list>
51                         <value>/js</value>
52                         <value>/css</value>
53                         <value>/images</value>
54                     </list>
55                 </property>
56             </bean>
57         </mvc:interceptor>
58     </mvc:interceptors>
59 </beans>

View Code

 

时间: 2024-11-03 20:50:22

springMVC的拦截器的相关文章

【SpringMVC】SpringMVC配置拦截器 mvc:exclude-mapping 报错

转载请注明出处http://blog.csdn.net/qq_26525215 本文源自[大学之旅_谙忆的博客] 今天写SpringMVC的拦截器的时候遇到这样一个错误 Element mvc:exclude-mapping is not allowed here. <!-- SpringMVC拦截器 --> <mvc:interceptors> <mvc:interceptor> <mvc:mapping path="/user/*"/>

springmvc的拦截器,怎么设置不拦截的url

问题描述 <!-- 默认首页 --><mvc:view-controller path="/" view-name="redirect:/loginpage" /><!-- 拦截器 --><mvc:interceptors><mvc:interceptor><mvc:mapping path="/**"/><mvc:exclude-mapping path="

SpringMVC中使用Interceptor拦截器

SpringMVC 中的Interceptor 拦截器也是相当重要和相当有用的,它的主要作用是拦截用户的请求并进行相应的处理.比如通过它来进行权限验证,或者是来判断用户是否登陆,或者是像12306 那样子判断当前时间是否是购票时间.  一.定义Interceptor实现类  SpringMVC 中的Interceptor 拦截请求是通过HandlerInterceptor 来实现的.在SpringMVC 中定义一个Interceptor 非常简单,主要有两种方式,第一种方式是要定义的Interc

SpringMVC 中的Interceptor 拦截器

  1.配置拦截器 在springMVC.xml配置文件增加: <mvc:interceptors>  <!-- 日志拦截器 -->  <mvc:interceptor>   <mvc:mapping path="/**" />   <mvc:exclude-mapping path="/static/**" />   <bean class="拦截器java代码路径" />

SpringMVC拦截器实现登录认证_java

博客以Demo的形式讲诉拦截器的使用 项目结构如图: 需要的jar:有springMVC配置需要的jar和jstl需要的jar SpringMVC包的作用说明: aopalliance.jar:这个包是AOP联盟的API包,里面包含了针对面向切面的接口.通常spring等其它具备动态织入功能的框架依赖这个jar spring-core.jar:这个jar 文件包含Spring 框架基本的核心工具类.Spring 其它组件要都要使用到这个包里的类,是其它组件的基本核心,当然你也可以在自己的应用系统

springMvc源码学习之:spirngMvc的拦截器使用

    SpringMVC 中的Interceptor 拦截器也是相当重要和相当有用的,它的主要作用是拦截用户的请求并进行相应的处理.比如通过它来进行权限验证,或者是来判断用户是否登陆,或者是像12306 那样子判断当前时间是否是购票时间.    一.定义Interceptor实现类      SpringMVC 中的Interceptor 拦截请求是通过HandlerInterceptor 来实现的.在SpringMVC 中定义一个Interceptor 非常简单,主要有两种方式,第一种方式是

SpringMVC 中的Interceptor 拦截器(HandlerInteceptor)

作用 一切请求都可以进去拦截,然后添加前后的处理逻辑 有点像是AOP 可以用在 1.权限检查:如登录检测,进入处理器检测检测是否登录,如果没有直接返回到登录页面: 2.像12306 那样子判断当前时间是否是购票时间. 3.日志记录:记录请求信息的日志,以便进行信息监控.信息统计.计算PV(Page View)等. 4.性能监控:有时候系统在某段时间莫名其妙的慢,可以通过拦截器在进入处理器之前记录开始时间,在处理完后记录结束时间,从而得到该请求的处理时间(如果有反向代理,如apache可以自动记录

Spring MVC拦截器实现分析

Spring MVC拦截器实现分析 一.Servlet Filter与Spring interceptor的执行顺序 Filter有顺序吗?我们怎么控制filter的执行顺序.通过Tomcat的代码分析,servlet在Filter执行完成后才调用,如有多个filter怎么控制执行顺序,首先会想到在web.xml配置某个参数,例如order之类的,但查找一下一番,servlet并没有这个参数.试试filter Mapping的配置的先后顺序,果然有效,原来filter的执行顺序就考filter

ajax-springmvc 登录拦截器

问题描述 springmvc 登录拦截器 拦截器起到了作用,跳到了登陆页面,登录页面是通过ajax提交请求给后台的,后台执行完了之后会返回一个map给ajax的success方法,从而进行页面的跳转.可是现在的问题是,后台执行了,但是跳不回前台,map也传回不去,更不说页面的跳转了. 解决方案 SpringMVC 登录拦截器实现springMVC之拦截器SpringMVC拦截器实现登录控制 解决方案二: 小机器人已经给你答案了: 1.不要拦截此跳转: 2.登录在后台执行了后,如果登录成功,直接更