SpringMVC拦截器初步使用
- 定义一个类,继承HandlerInterceptor接口,并实现该接口的preHandle()、postHandle()、afterCompletion()三个方法。三个方法分别什么时候调用下面代码注释上写了。定义一个类,继承HandlerInterceptor接口,并实现该接口的preHandle()、postHandle()、afterCompletion()三个方法。三个方法分别什么时候调用下面代码注释上写了。
package fei.springmvc.interceptor;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/**
* @author xiaoshijiu
* @location SpringMVC/fei.springmvc.interceptor
* @date 2019/3/4
*/
public class LoginInterception implements HandlerInterceptor {
//处理器方法映射之前执行
//返回true,放行;false,不放行
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
System.out.println("处理器方法映射之前执行");
return true;
}
//处理器方法映射执行之后会自动调用
@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
System.out.println("处理器方法映射执行之后会自动调用");
}
//所有请求完成之后调用
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
System.out.println("所有请求完成之后调用");
}
}
- 在springmvc的配置文件里面进行配置
<mvc:interceptors>
<!--自定义拦截器(拦截所有请求)-->
<bean class="fei.springmvc.interceptor.FristInterception"></bean>
<!--自定义拦截器(拦截指定请求)-->
<mvc:interceptor>
<mvc:mapping path="/intercep"/>
<bean class="fei.springmvc.interceptor.LoginInterception"></bean>
</mvc:interceptor>
</mvc:interceptors>
在<mvc:interceptors> </mvc:interceptors>
里面直接配置bean则是拦截所有请求;在里面配置<mvc:interceptor> </mvc:interceptor>
则可以通过配置 <mvc:mapping path="/intercep"/>
拦截指定请求,或者配置<mvc:exclude-mapping path=""/>
拦截除此之外的所有请求
- 完成工作,发送请求测试
注意点
- 进行用户是否登录的验证时,可以使用这个preHandle()方法判断session中是否有该用户,如果session中不存在,往往需要跳转到登陆页面,这里使用重定向或者请求转发的方式
//请求转发
request.getRequestDispatcher("WEB-INF/pages/login.jsp").forward(request,response);
//重定向
response.sendRedirect("login.jsp");
return false;
-
执行顺序(以两个为例)
2.1. 两个拦截器的preHandle()方法都返回true
两个拦截器测试
package fei.springmvc.interceptor;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/**
* @author xiaoshijiu
* @location SpringMVC/fei.springmvc.interceptor
* @date 2019/3/4
*/
public class FristInterception implements HandlerInterceptor {
//处理器方法映射之前执行
//返回true,放行;false,不放行
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
System.out.println("处理器方法映射之前执行1");
return true;
}
//处理器方法映射执行之后会自动调用
@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
System.out.println("处理器方法映射执行之后会自动调用1");
}
//所有请求完成之后调用
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
System.out.println("所有请求完成之后调用1");
}
}
package fei.springmvc.interceptor;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/**
* @author xiaoshijiu
* @location SpringMVC/fei.springmvc.interceptor
* @date 2019/3/4
*/
public class SecondInterception implements HandlerInterceptor {
//处理器方法映射之前执行
//返回true,放行;false,不放行
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
System.out.println("处理器方法映射之前执行2");
return true;
}
//处理器方法映射执行之后会自动调用
@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
System.out.println("处理器方法映射执行之后会自动调用2");
}
//所有请求完成之后调用
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
System.out.println("所有请求完成之后调用2");
}
}
xml中配置
<mvc:interceptors>
<!--自定义拦截器(拦截所有请求)-->
<bean class="fei.springmvc.interceptor.FristInterception"></bean>
<!--自定义拦截器(拦截所有请求)-->
<bean class="fei.springmvc.interceptor.SecondInterception"></bean>
</mvc:interceptors>
测试结果
可以看到preHandle()方法是按顺序执行,postHandle()和afterCompletion()方法是倒序执行
(这里的顺序是指在xml配置文件里面拦截器配置的先后顺序)
原因解释
SpringMVC拦截器执行顺序原理解释
2.2. 第一个拦截器的preHandle()方法返回true,第二个返回false
测试结果
可以看到两个拦截器的preHandle()方法按顺序执行了,另外还有第一个拦截器的afterCompletion()方法执行了
原因解释
SpringMVC拦截器执行顺序原理解释
2.3. 第一个拦截器的preHandle()方法返回false,第二个返回true
测试结果
可以看到只调用了第一个拦截器的preHandle()方法
原因解释
SpringMVC拦截器执行顺序原理解释