提示:这里可以添加本文要记录的大概内容:
用户登录验证的时候经常会用到
Spring MVC中的拦截器(Interceptor)类似于Servlet中的过滤器(Filter)
它主要用于拦截用户请求并作相应的处理。
例如通过拦截器可以进行权限验证、记录请求信息的日志、判断用户是否登录等。
登录拦截器:
public class LoginInterceptor implements HandlerInterceptor{
@Override
public boolean preHandle(HttpServletRequest request,
HttpServletResponse response, Object handler) throws Exception {
// 获取请求的URL
String url = request.getRequestURI();
// URL:除了login.jsp是可以公开访问的,其它的URL都进行拦截控制
if(url.indexOf("/login")>=0){
return true;
}
// 获取Session
HttpSession session = request.getSession();
User user = (User) session.getAttribute("USER_SESSION");
// 判断Session中是否有用户数据,如果有,则返回true,继续向下执行
if(user != null){
return true;
}
// 不符合条件的给出提示信息,并转发到登录页面
request.setAttribute("msg", "您还没有登录,请先登录!");
request.getRequestDispatcher("/WEB-INF/jsp/login.jsp")
.forward(request, response);
return false;
}
@Override
public void postHandle(HttpServletRequest request,
HttpServletResponse response, Object handler,
ModelAndView modelAndView) throws Exception {
}
@Override
public void afterCompletion(HttpServletRequest request,
HttpServletResponse response, Object handler, Exception ex)
throws Exception {
}
}
登录代码:
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>用户登录</title>
</head>
<body>
${msg}
<form action="${pageContext.request.contextPath }/login"
method="POST">
用户名:<input type="text" name="username"/><br />
密 码:
<input type="password" name="password"/><br />
<input type="submit" value="登录" />
</form>
</body>
</html>
提示:以下是本篇文章正文内容,下面案例可供参考

比如说你去一个网站要下载某篇文章或者浏览文章等等,但你点开后却跑到一个登录或者注册页面,很多时候这就是拦截器功能,对这个请求进行拦截


通过实现HandlerInterceptor接口,或继承HandlerInterceptor接口的实现类
(如 HandlerInterceptorAdapter)来定义
以实现HandlerInterceptor接口方式为例,自定义拦截器类的代码如下:
先定义一个类:CustomInterceptor,然后实现HandlerInterceptor 接口
public class CustomInterceptor implements HandlerInterceptor {
public boolean preHandle(HttpServletRequest request,
HttpServletResponse response,Object handler)throws Exception {
return false;
}
public void postHandle(HttpServletRequest request,
HttpServletResponse response, Object handler,
ModelAndView modelAndView) throws Exception {
}
public void afterCompletion(HttpServletRequest request,
HttpServletResponse response,Object handler,Exception ex) throws Exception {
}
}
preHandle方法:
该方法会在控制器方法前执行,其返回值表示是否中断后续操作
当其返回值为true 时,表示继续向下执行;
当其返回值为false时,会中断后续的所有操作。
postHandle方法:
该方法会在控制器方法调用之后,且解析视图之前执行
可以通过此方法对请求域中的模型和视图做出进一步的修改。
afterCompletion方法:
该方法会在整个请求完成,即视图渲染结束之后执行
可以通过此方法实现一些资源清理、记录日志信息等工作。
要使自定义的拦截器类生效,还需要在Spring MVC的配置文件少进行配置。
也就是只有配置之后,上面拦截器定义的类:CustomInterceptor,才能用
实际项目中会有很多个URL请求
<!-- 配置拦截器 -->
<mvc:interceptors>
<!--使用bean直接定义在<mvc:interceptors>下面的拦截器将拦截所有请求-->
<bean class="com.itheima.interceptor.CustomInterceptor"/>
<mvc:interceptor>
<mvc:mapping path="/**"/> <!-- 斜杆**配置,表示拦截所有路径 -->
<mvc:exclude-mapping path=""/> <!-- 配置不需要拦截的路径,也就是排除""内的地址 -->
<bean class="com.itheima.interceptor.Interceptor1"/>
</mvc:interceptor>
<mvc:interceptor>
<mve:mapping path="/hello"/> <!-- /hello表示拦截所有以“/hello” 结尾的路径 -->
<bean class="com.itheima.interceptor.Interceptor2"/>
</mvc:interceptor>
<mvc:interceptor>
<mvc:mapping path="/**" />
<mvc:exclude-mapping path="/hello"/> <!-- 拦截所有的,后续带/hello 除外 -->
<bean class="com.itheima.interceptor.LoginInterceptor" />
</mvc:interceptor>
...
</mvc:interceptors>
注意:
mvc:interceptor中的子元素必须按照上述代码的配置顺序进行编写,否则文件会报错。
在运行程序时,拦截器的执行是有一定顺序的,该顺序与配置文件中所定义的拦截器的顺序相关。
单个拦截器,在程序中的执行流程如下图所示:

多个拦截器(假设有两个拦截器 Interceptor1和 Interceptor2,并且在配置文件中,Interceptor1拦截器配置在前),在程序中的执行流程如下图所示:

从图可以看出,当有多个拦截器同时工作时,
它们的 preHandle( )方法会按照配置文件中拦截器的配置顺序执行,
而它们的 postHandle( )方法和 afterCompletion( )方法则会按照配置顺序的反序执行。