Spring MVC—拦截器详解

JAVA 2023-07-05 17:29:38
60阅读

  今日便是把相关拦截器的专业知识做一个汇总。

强烈推荐收看

大型厂面试真题聚集地:阿里三面 腾讯官方二面 支付宝钱包三面 拼多多平台二面 字节数四面 淘宝网五面_bilbil (゜-゜)つロ 干杯~-bilibili了不起!B站最齐互联网最底层归纳:TCP、Sockt、三次握手、四次挥手、NIO、Epoll、时分复用(附送源代码、思维脑图)阿里杰出系统架构师解读最“细”的spring源代码(附送授课材料和源代码)Java系统架构师必会六大关键知识要点:线程同步、JVM、策略模式、MySQL、Redis、ZooKeeper你从没听过的全新升级版本号!Tomcat、TCP/IP、IO、分布式系统分布式架构详解

  

1.拦截器简述

1.1 什么叫拦截器?

  Spring MVC中的拦截器(Interceptor)类似Servlet中的过滤装置(Filter),它关键用以阻拦客户要求并且做好相对的解决。比如根据拦截器能够开展管理权限认证、纪录要求信息的系统日志、分辨客户是不是登陆等。
要应用Spring MVC中的拦截器,就必须对拦截器类开展界定和配备。一般拦截器类能够根据二种方法来界定。
1.根据完成HandlerInterceptor接口,或承继HandlerInterceptor接口的完成类(如HandlerInterceptorAdapter)来界定。

  2.根据完成WebRequestInterceptor接口,或承继WebRequestInterceptor接口的完成类来界定。

  以完成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 { } }

  所述编码中,自定拦截器完成了HandlerInterceptor接口,并完成了接口中的三个方法:

  • preHandle() 方法:该方法会在控制板方法前执行,其返回值表明是不是终断事后实际操作。当其返回值为true时,表明再次往下执行;
    当其返回值为false时,会终断事后的全部实际操作(包含启用下一个拦截器和控制板类中的方法执行等)。
  • postHandle()方法:该方法会在控制板方法启用以后,且分析主视图以前执行。能够根据此方法对要求域中的实体模型和主视图作出进一步的改动。
  • afterCompletion()方法:该方法会在全部要求进行,即主视图3D渲染完毕以后执行。能够根据此方法完成一些資源清除、纪录系统日志信息等工作中。

1.2 拦截器的配备

  开发设计拦截器如同开发设计servlet或是filter一样,都必须在环境变量开展配备,配备编码以下:

  <!--配备拦截器--> <; <!--<bean class="com.ma.interceptor.CustomeInterceptor" />--> <!--拦截器1--> <; <!--配备拦截器的功效途径--> < path="/**"/> < path=""/> <!--界定在<; <bean class="com.ma.interceptor.Intercptor1"/> </; <!--拦截器2--> <; < path="/hello"/> <bean class="com.ma.interceptor.Interceptor2"/> </;

  上边的编码中,< 中界定。如所述编码中 path 的特性值“/**” 表明阻拦全部途径,“/hello” 表明阻拦全部以 “/hello” 末尾的途径。假如在要求途径中包括不用阻拦的內容,还能够根据<
留意:<; <; <bean>,不然文档会出错。

2. 拦截器的执行步骤

2.1 单独拦截器的执行步骤

  在运作程序流程时,拦截器的执行是有一定次序的,该次序与环境变量中所界定的拦截器的次序有关。
单独拦截器,在程序流程中的执行步骤如下图所显示:

  

  

  1.程序流程先执行preHandle()方法,假如该方法的返回值为true,则程序流程会再次往下执行CPU中的方法,不然将已不往下执行。

  2.在业务流程CPU(即控制板Controller类)解决完要求后,会执行postHandle()方法,随后会根据DispatcherServlet向手机客户端回到回应。

  3.在DispatcherServlet解决完要求后,才会执行afterCompletion()方法。

  检测实例:
根据一个测试代码来认证它的执行步骤。
新创建一个web项目,准备好SpringMVC程序执行所必须的JAR包,在web.xml中配备前端开发过滤器和复位载入信息。
新创建一个检测controller,编码以下:

  /** * @author mz * @version V1.0 * @Description: 拦截器检测 */@Controllerpublic class HelloController { @RequestMapping("/hello") public String Hello() { System.out.println("Hello!"); return "success"; }}

  随后,新创建一个拦截器,完成HandlerInterceptor接口,并完成在其中的方法。

  /** * @author mz * @version V1.0 * @Description: 完成了HandlerInterceptor接口的自定拦截器类 */public class CustomeInterceptor implements HandlerInterceptor { @Override public boolean preHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o) throws Exception { System.out.println("CustomInterceptor....preHandle"); //对电脑浏览器的要求开展海关放行解决 return true; } @Override public void postHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, ModelAndView modelAndView) throws Exception { System.out.println("CustomInterceptor....postHandle"); } @Override public void afterCompletion(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, Exception e) throws Exception { System.out.println("CustomInterceptor....afterCompletion"); }}

  在环境变量中配备拦截器。

  <beans xmlns="; ; ; ; ; <!--定义组件扫描器,指定需要扫描的包--> < base-package="com.ma.controller"/> <!-- 配置视图解析器 --> <bean class="org.springframework.web.servlet.view.InternalResourceViewResolver"> <property name="prefix" value="/WEB-INF/jsp/"/> <property name="suffix" value=".jsp"/> </bean> <!--配置拦截器--> <; <bean class="com.ma.interceptor.CustomeInterceptor" /> </beans>

  把项目发布到tomcat中,运行测试:

  

2.2 多个拦截器的执行流程

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

  

  

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

  /** * @author mz * @version V1.0 * @Description: 第一个拦截器 */public class Intercptor1 implements HandlerInterceptor { @Override public boolean preHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o) throws Exception { System.out.println("Interceptor1....preHandle"); return true; } @Override public void postHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, ModelAndView modelAndView) throws Exception { System.out.println("Interceptor1....postHandle"); } @Override public void afterCompletion(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, Exception e) throws Exception { System.out.println("Interceptor1....afterCompletion"); }/** * @author mz * @version V1.0 * @Description: 第二个拦截器 */public class Interceptor2 implements HandlerInterceptor { @Override public boolean preHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o) throws Exception { System.out.println("Interceptor2....preHandle"); return true; } @Override public void postHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, ModelAndView modelAndView) throws Exception { System.out.println("Interceptor2....postHandle"); } @Override public void afterCompletion(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, Exception e) throws Exception { System.out.println("Interceptor2....afterCompletion"); }}

  添加配置信息:

  <!--拦截器1--> <; <!--配置拦截器的作用路径--> < path="/**"/> <!--定义在<; <bean class="com.ma.interceptor.Intercptor1"/> </; <!--拦截器2--> <; < path="/hello"/> <bean class="com.ma.interceptor.Interceptor2"/> </;

  测试运行:

  
从结果可以看出,执行的顺序和图片中是一样的。

  如果第一个拦截器return true; 而第二个拦截器 return false;结果如下:

  

推荐观看

大厂面试真题集结地:阿里三面+腾讯二面+支付宝三面+拼多多二面+字节四面+淘宝五面_哔哩哔哩 (゜-゜)つロ 干杯~-bilibili厉害了!B站最全网络底层汇总:TCP、Sockt、三次握手、四次挥手、NIO、Epoll、多路复用(附赠源码、脑图)阿里资深架构师讲解最“细”的spring源码(附赠讲课资料和源码)Java架构师必会六大核心知识点:多线程、JVM、设计模式、MySQL、Redis、ZooKeeper你从未听过的全新版本!Tomcat、TCP/IP、IO、分布式微服务架构全解

  

小结

  首先学习如何在Spring MVC项目中定义和配置拦截器,然后了解单个拦截器和多个拦截器的执行流程。

the end
免责声明:本文不代表本站的观点和立场,如有侵权请联系本站删除!本站仅提供信息存储空间服务。