概述

首先声明一下,这里所说的拦截器是 SpringMVC 的拦截器 HandlerInterceptor。使用SpringMVC 拦截器需要做如下操作:

  1. 创建拦截器类需要实现 HandlerInterceptor
  2. 在 xml 配置文件中配置该拦截器,具体配置代码如下:
  1. <mvc:interceptors>
  2. <mvc:interceptor>
  3. <!-- /test/** 这个是拦截路径以/test开头的所有的URL-->
  4. <mvc:mapping path="/**"/><!—这个是拦截说有的路径-->
  5. <!-- 配置拦截器类路径-->
  6. <bean class="cn.ljk.springmvc.controller.MyInterceptor"></bean>
  7. <!-- 配置不拦截器URL路径-->
  8. <mvc:exclude-mapping path="/fore/**"/>
  9. </mvc:interceptor>
  10. </mvc:interceptors>

因为在SpringBoot 中没有 xml 文件,所以SpringBoot 为我们提供 Java Config 的方式来配置拦截器。配置方式有2种:

  1. 继承 WebMvcConfigurerAdapter (官方已经不建议使用)
  2. 实现 WebMvcConfigurer

接下来开始 SpringBoot 整合拦截器操作详细介绍!

整合拦截器实战操作

第一步:声明拦截器类

通过实现 HandlerInterceptor 来完成。具体代码如下:

  1. public class LoginInterceptor implements HandlerInterceptor{}

第二步:实现 HandlerInterceptor 3 个拦截方法

  • preHandle:Controller逻辑执行之前进行拦截
  • postHandle:Controller逻辑执行完毕但是视图解析器还为进行解析之前进行拦截
  • afterCompletion:Controller逻辑和视图解析器执行完毕进行拦截

实际开发中 preHandle使用频率比较高,postHandle 和 afterCompletion操作相对比较少。

在下面的代码中 preHandle 方法中定义拦截所有访问项目 URL并进行日志信息记录。postHandle 中在视图解析前进行拦截,通过 Model 在次添加数据Request域中。

afterCompletion 暂时没有想到使用场景,如果有使用过的场景可以在下面评论区中进行评论。

拦截器详细代码如下:

  1. public class LoginInterceptor implements HandlerInterceptor{
  2. private Logger log = LoggerFactory.getLogger(LoginInterceptor.class);
  3. //ControllerController逻辑执行之前
  4. public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
  5. log.info("preHandle....");
  6. String uri = request.getRequestURI();
  7. log.info("uri:"+ uri);
  8. if (handler instanceof HandlerMethod) {
  9. HandlerMethod handlerMethod = (HandlerMethod) handler;
  10. log.info("拦截 Controller:"+ handlerMethod.getBean().getClass().getName());
  11. log.info("拦截方法:"+handlerMethod.getMethod().getName());
  12. }
  13. return true;
  14. }
  15. //Controller逻辑执行完毕但是视图解析器还为进行解析之前
  16. @Override
  17. public void postHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, ModelAndView modelAndView) throws Exception {
  18. log.info("postHandle....");
  19. Map<String,Object>map=modelAndView.getModel();
  20. map.put("msg","postHandle add msg");
  21. }
  22. //Controller逻辑和视图解析器执行完毕
  23. @Override
  24. public void afterCompletion(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, Exception e) throws Exception {
  25. log.info("afterCompletion....");
  26. }
  27. }

第三步:Java Config 的方式来配置拦截器

继承 WebMvcConfigurerAdapter 方式

通过继承 WebMvcConfigurerAdapter并重写 addInterceptors方法,通过其参数 InterceptorRegistry将拦截器注入到 Spring的上下文中。

另外拦截路径和不拦截的路径通过InterceptorRegistry 的 addPathPatterns和 excludePathPatterns方法进行设置。

这种方式官方已经不建议使用,因为官方已将 WebMvcConfigurerAdapter 标记为@Deprecated 了。

  1. @Deprecated
  2. public abstract class WebMvcConfigurerAdapter implements WebMvcConfigurer {

继承 WebMvcConfigurerAdapter 方式具体代码如下:

  1. @Configuration
  2. public class InterceptorConfigByExtendsWebMvcConfigurerAdapter extends WebMvcConfigurerAdapter{
  3. @Bean
  4. public LoginInterceptor loginInterceptor(){
  5. return new LoginInterceptor();
  6. }
  7. public void addInterceptors(InterceptorRegistry registry) {
  8. registry.addInterceptor(loginInterceptor()).addPathPatterns("/**").excludePathPatterns("/*.html");
  9. }
  10. }

实现 WebMvcConfigurer 方式

通过实现 WebMvcConfigurer 接口并实现 addInterceptors方法,其他操作和继承 WebMvcConfigurerAdapter方式一样。具体代码如下:

  1. ```java
  2. @Configuration
  3. public class InterceptorConfigByImplWebMvcConfigurer implements WebMvcConfigurer{
  4. @Bean
  5. public LoginInterceptor loginInterceptor(){
  6. return new LoginInterceptor();
  7. }
  8. @Override
  9. public void addInterceptors(InterceptorRegistry registry) {
  10. registry.addInterceptor(loginInterceptor()).addPathPatterns("/**").excludePathPatterns("/*.html");
  11. }
  12. }
  13. ```

测试

编写普通Controller,具体代码如下:

  1. @Controller
  2. public class IndexController {
  3. @GetMapping("/index")
  4. public String index(ModelAndView modelAndView){
  5. return "index";
  6. }
  7. }

在 src/main/resource 下的 templates目录下创建 IndexController访问页面 index.ftl, 代码如下:

  1. <h1>${msg}</h1>

由于我这里使用的是 Freemarker当页面使用,说以需要引入 Freemarker starter依赖,具体点如下:

  1. <dependency>
  2. <groupId>org.springframework.boot</groupId>
  3. <artifactId>spring-boot-starter-freemarker</artifactId>
  4. </dependency>

通过游览器访问 localhost:8080/sbe/index,具体访问效果如下:

如上图所示在视图解析前通过 Model在次添加数据到 Request域中的msg 成功显示出来了!

日志输出信息如下:拦截地址和拦截Controller 和具体方法进行日志输出

  1. 2019-09-24 15:53:04.144 INFO 7732 --- [nio-8080-exec-1] o.a.c.c.C.[Tomcat].[localhost].[/sbe] : Initializing Spring DispatcherServlet 'dispatcherServlet'
  2. 2019-09-24 15:53:04.145 INFO 7732 --- [nio-8080-exec-1] o.s.web.servlet.DispatcherServlet : Initializing Servlet 'dispatcherServlet'
  3. 2019-09-24 15:53:04.153 INFO 7732 --- [nio-8080-exec-1] o.s.web.servlet.DispatcherServlet : Completed initialization in 8 ms
  4. 2019-09-24 15:53:04.155 INFO 7732 --- [nio-8080-exec-1] c.lijunkui.interceptor.LoginInterceptor : preHandle....
  5. 2019-09-24 15:53:04.155 INFO 7732 --- [nio-8080-exec-1] c.lijunkui.interceptor.LoginInterceptor : uri:/sbe/index
  6. 2019-09-24 15:53:04.155 INFO 7732 --- [nio-8080-exec-1] c.lijunkui.interceptor.LoginInterceptor : 拦截 Controllercn.lijunkui.controller.IndexController
  7. 2019-09-24 15:53:04.155 INFO 7732 --- [nio-8080-exec-1] c.lijunkui.interceptor.LoginInterceptor : 拦截方法:index
  8. 2019-09-24 15:53:04.156 INFO 7732 --- [nio-8080-exec-1] c.lijunkui.interceptor.LoginInterceptor : postHandle....
  9. 2019-09-24 15:53:04.161 INFO 7732 --- [nio-8080-exec-1] c.lijunkui.interceptor.LoginInterceptor : afterCompletion....

小结

SpringBoot 2 整合拦截器和整合 Filter的操作很像,都是通过一个注册类将其注入到Spring的上下文中,只不过Filter使用的是 FilterRegistrationBean 而 拦截器使用的是 InterceptorRegistry。

个人觉得比使用 xml 配置的方式更为简单了,如果你还没有在 SpringBoot 项目中使用过拦截器,赶快来操作一下吧!

代码示例

具体代码示例请在我的GitHub 仓库 springbootexamples 中模块名为 spring-boot-2.x-interceptor 项目中进行查看

GitHub:https://github.com/zhuoqianmingyue/springbootexamples

玩转 SpringBoot 2 快速整合拦截器的更多相关文章

  1. 玩转 SpringBoot 2 快速整合 | JSP 篇

    前言 JavaServer Pages(JSP)技术使Web开发人员和设计人员能够快速开发和轻松维护利用现有业务系统的信息丰富的动态Web页面. 作为Java技术系列的一部分,JSP技术可以快速开发独 ...

  2. 玩转 SpringBoot 2 快速整合 | 丝袜哥(Swagger)

    概述 首先让我引用 Swagger 官方的介绍: Design is the foundation of your API development. Swagger makes API design ...

  3. 玩转 SpringBoot 2 快速整合 Filter

    概述 SpringBoot 中没有 web.xml, 我们无法按照原来的方式在 web.xml 中配置 Filter .但是我们可以通过 JavaConfig(@Configuration +@Bea ...

  4. 玩转 SpringBoot 2 快速整合 | FreeMarker篇

    FreeMarker 介绍 Apache FreeMarker™是一个模板引擎:一个Java库,用于根据模板和更改数据生成文本输出(HTML网页,电子邮件,配置文件,源代码等).模板是用FreeMar ...

  5. 玩转 SpringBoot 2 快速整合 | Thymeleaf 篇

    前言 Thymeleaf是一个适用于Web和独立环境的现代服务器端Java模板引擎. Thymeleaf的主要目标是为您的开发工作流程带来优雅的自然模板 - 可以在浏览器中正确显示的HTML,也可以用 ...

  6. 玩转 SpringBoot 2 之整合 JWT 下篇

    前言 在<玩转 SpringBoot 2 之整合 JWT 上篇> 中介绍了关于 JWT 相关概念和JWT 基本使用的操作方式.本文为 SpringBoot 整合 JWT 的下篇,通过解决 ...

  7. 使用Springboot + Gradle快速整合Mybatis-Plus

    使用Springboot + Gradle快速整合Mybatis-Plus 作者:Stanley 罗昊 [转载请注明出处和署名,谢谢!] MyBatis-Plus(简称 MP)是一个 MyBatis ...

  8. 玩转 SpringBoot 2 快速搭建 | RESTful Api 篇

    概述 RESTful 是一种架构风格,任何符合 RESTful 风格的架构,我们都可以称之为 RESTful 架构.我们常说的 RESTful Api 是符合 RESTful 原则和约束的 HTTP ...

  9. 玩转 SpringBoot 2 之整合 JWT 上篇

    前言 该文主要带你了解什么是 JWT,以及JWT 定义和先关概念的介绍,并通过简单Demo 带你了解如何使用 SpringBoot 2 整合 JWT. 介绍前在这里我们来探讨一下如何学习一门新的技术, ...

随机推荐

  1. Java深层复制方式

    为什么需要深层复制 Object 的 clone() 方法是浅层复制(但是 native 很高效).另外,Java 提供了数组和集合的复制方法,分别是 Arrays.copy() 和 Collecti ...

  2. 堆、栈、内存分配、==、equals、hashcode详解(转载)

    问题的引入: 问题一:String str1 = "abc";String str2 = "abc";System.out.println(str1==str2 ...

  3. mysql类似oracle rownum写法

    rownum是oracle才有的写法,rownum在oracle中可以用于取第一条数据,或者批量写数据时限定批量写的数量等 mysql取第一条数据写法 SELECT * FROM t order by ...

  4. 爬虫——网页解析利器--re & xpath

    正则解析模块re re模块使用流程 方法一 r_list=re.findall('正则表达式',html,re.S) 方法二  创建正则编译对象 pattern = re.compile('正则表达式 ...

  5. NLP(十九) 双向LSTM情感分类模型

    使用IMDB情绪数据来比较CNN和RNN两种方法,预处理与上节相同 from __future__ import print_function import numpy as np import pa ...

  6. POJ3233 Matrix Power Series 矩阵快速幂 矩阵中的矩阵

    Matrix Power Series Time Limit: 3000MS   Memory Limit: 131072K Total Submissions: 27277   Accepted:  ...

  7. CF1005D Polycarp and Div 3 思维

    Polycarp and Div 3 time limit per test 3 seconds memory limit per test 256 megabytes input standard ...

  8. The Sultan's Successors UVA - 167

    the squares thus selected sum to a number at least as high as one already chosen by the Sultan. (For ...

  9. 2017 省赛选拨 火车入站 CSU 1757 模拟

    1757: 火车入站 Submit Page   Summary   Time Limit: 1 Sec     Memory Limit: 128 Mb     Submitted: 512     ...

  10. Linux_Day001-002章常用命令

    Linux操作系统的组成 以下符号的意义. 输出重定向和输入重定向的知识点 echo 把后面的文字显示出来 xargs 分组, -n 分为n组  xargs -n 1.txt (完整命令:xargs ...