目录

  • `Interceptor` 拦截器
    • 拦截器概述
    • 拦截器中方法的执行流程
    • 拦截器的配置
      • 传统项目拦截器的配置
      • `SpringBoot` 项目拦截器的配置
        • 实现 `HandlerInterceptor` 接口编写拦截器
        • 实现 `WebMvcConfigurer` 接口注册拦截器
      • 多个拦截器的执行顺序
  • `Filter` 过滤器
    • 过滤器概述
    • 过滤器的配置
      • 传统项目过滤器的配置
      • `SpringBoot` 项目过滤器的配置
        • 方式一:`@WebServlet + @ServletComponentScan` 注解
          • `@WebFilter` 注解开发过滤器
          • 启动类增加 `@ServletComponentScan`
        • 方式二:`FilterRegistrationBean` 注册
          • 实现 `Filter` 接口
          • 在配置类中注册该过滤器
  • `Interceptor` 和 `Filter` 小结

Interceptor 拦截器

拦截器概述

HandlerInterceptor 接口,该接口提供了拦截器的功能,如果自定义拦截器就要实现该接口HandlerInterceptor 源码如下

public interface HandlerInterceptor {// 该方法会在控制器方法前执行default boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler)throws Exception {return true;}// 该方法会在控制器方法调用之后,且解析视图之前执行default void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler,@Nullable ModelAndView modelAndView) throws Exception {}// 该方法会在整个请求完成,即视图渲染结束之后执行default void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler,@Nullable Exception ex) throws Exception {}
}

Interceptor 依赖于 web 框架,我们经常在 SpringMVC 中用到该配置,在这个场景下 Interceptor 就依赖于 SpringMVC 框架。Interceptor 基于 Java 的反射机制,属于AOP 的一种运用

  • 由于拦截器是基于 web 框架的调用,因此可以使用 Spring 的依赖注入进行一些业务操作,同时一个拦截器实例在一个 Controller 生命周期之内可以多次调用
  • 只能对 Controller 请求进行拦截,对其他的一些比如直接访问静态资源的请求则没办法进行拦截处理

拦截器中方法的执行流程

  • 请求到达 DispatcherServletDispatcherServlet 发送至 Interceptor ,执行 preHandle() 方法,该方法会返回一个布尔值。如果为 false ,则结束所有流程:如果为 true , 则执行下一步
  • 请求达到 Controller,执行处理器逻辑,它包含控制器的功能
  • 执行 postHandle() 方法
  • 执行视图解析和视图渲染
  • 执行 afterCompletion() 方法

拦截器的配置

传统项目拦截器的配置

基于 SpringMVC 的项目 ,我们之前的案例配置拦截器的方式如下

SpringBoot 项目拦截器的配置

实现 HandlerInterceptor 接口编写拦截器

继承 HandlerInterceptorAdapter 也可以,它是 HandlerInterceptor 的子类

public class MyInterceptor implements HandlerInterceptor {// preHandle在执行Controller之前执行@Overridepublic boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler)throws Exception {System.out.println("MyInterceptor-处理器执行前方法preHandle,返回true则不拦截后续的处理");return true;}// postHandle在请求执行完之后 渲染ModelAndView返回之前执行@Overridepublic void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler,ModelAndView modelAndView) throws Exception {HandlerInterceptor.super.postHandle(request, response, handler, modelAndView);System.out.println("MyInterceptor-处理器处理后方法postHandle");}// afterCompletion在整个请求执行完毕后执行,无论是否发生异常都会执行@Overridepublic void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex)throws Exception {HandlerInterceptor.super.afterCompletion(request, response, handler, ex);System.out.println("MyInterceptor-处理器完成后方法afterCompletion");}
}

实现 WebMvcConfigurer 接口注册拦截器

先说明下几个可以用来注册拦截器的类和接口

  • WebMvcConfigurerAdapterSpringBoot 2.0 以后的版本已失效
  • WebMvcConfigurationSupport: 不需要返回逻辑视图,可以选择继承此类
  • WebMvcConfigurer:返回逻辑视图,可以选择实现此方法,重写 addInterceptor() 方法
@Configuration
public class WebConfig implements WebMvcConfigurer {@Overridepublic void addInterceptors(InterceptorRegistry registry) {// 注册拦截器到 springMVC 机制, 然后它会返回一个拦截器注册InterceptorRegistration regist =  registry.addInterceptor(new MyInterceptor());// 指定拦截匹配模式,限制拦截器拦截请求regist.addPathPatterns("/artisan/interceptor/*");// 不拦截的路径regist.excludePathPatterns("/artisan/interceptor/exclude/*");}
}

多个拦截器的执行顺序

使用的是责任链模式的规则:对于 preHandle() 采用 先注册先执行,而 postHandle()afterCompletion() 则是 先注册后执行

Filter 过滤器

过滤器概述

过滤器 Filter,是在 Servlet 规范中定义的,是 Servlet 容器支持的,该接口定义在 javax.servlet 包下,主要是对客户端请求 HttpServletRequest 进行预处理,以及对服务器响应 HttpServletResponsen 进行后处理。Filter 接口源码如下

package javax.servlet;import java.io.IOException;public interface Filter {default void init(FilterConfig filterConfig) throws ServletException {}void doFilter(ServletRequest var1, ServletResponse var2, FilterChain var3) throws IOException, ServletException;default void destroy() {}
}

该接口包含了 Filter3 个生命周期:init()doFilter()destroy()

  • init()Servlet 容器在初始化 Filter 时,会触发 Filterinit() 方法,一般来说是当服务启动时,这个方法只调用一次,用于初始化 Filter
  • doFilter():当 init() 方法初始化 Filter 后,Filter 拦截到用户请求时,Filter 就开始工作了
void doFilter(ServletRequest var1, ServletResponse var2, FilterChain var3) throws IOException, ServletException;

Servlet 容器会将用户请求封装成 ServletRequest,而 doFilter() 参数中就 ServletRequest,这也就意味着允许给 ServletRequest 增加属性或者增加 header,也可以修饰 ServletReqest 或者 ServletResponse 来改变其行为

请注意最后一个参数 FilterChain var3,该接口定义如下

public interface FilterChain {void doFilter(ServletRequest var1, ServletResponse var2) throws IOException, ServletException;
}

该参数存在意味着,到达用户请求的真正方法之前,可能被多个过滤器进行过滤,这时 Filter.doFilter() 方法将触发 Filter 链条中下一个 Filter

  • destroy():顾名思义,该方法就是在 Servlet 容器要销毁 Filter 时触发,一般在应用停止的时候调用

过滤器的配置

传统项目过滤器的配置

传统项目配置使用 filter 的主要 2 个步骤

  • 实现 Filter 接口,实现其 doFilter() 方法
  • web.xml 文件中使用 <filter><filter-mapping> 元素对编写的 filter 类进行注册,并设置它所能拦截的资源
  • 可以编写多个 Filter,组成一个 Filter 链,根据 Filterweb.xml 文件中的注册顺序,决定先调用哪个 Filter

SpringBoot 项目过滤器的配置

方式一:@WebServlet + @ServletComponentScan 注解

@WebFilter 注解开发过滤器

@WebFilter 用于将一个类声明为过滤器,该注解将会在部署时被容器处理,容器将根据具体的属性配置将相应的类部署为过滤器

@WebFilter(filterName = "HttpFilter2", urlPatterns = "/*")
public class HttpFilter2 implements Filter {@Overridepublic void init(FilterConfig filterConfig) throws ServletException {System.out.println("HttpFilter2  init");Filter.super.init(filterConfig);}@Overridepublic void doFilter(ServletRequest request, ServletResponse response, FilterChain chain)throws IOException, ServletException {System.out.println("HttpFilter2  doFilter begin");HttpServletRequest req = (HttpServletRequest) request;HttpServletResponse res = (HttpServletResponse) response;System.out.println("HttpFilter2 name:" + request.getParameter("name"));// 将请求转发给过滤器链上下一个对象。这里的下一个指的是下一个filter,如果没有filter那就是请求的资源。chain.doFilter(request, response);System.out.println("HttpFilter2  doFilter end");}@Overridepublic void destroy() {System.out.println("HttpFilter2  destroy");Filter.super.destroy();}
}
启动类增加 @ServletComponentScan

使用 @ServletComponentScan 注解后,Servlet、Filter、Listener 可以直接通过 @WebServlet、@WebFilter、@WebListener 注解自动注册

方式二:FilterRegistrationBean 注册

实现 Filter 接口
public class HttpFilter implements Filter {@Overridepublic void init(FilterConfig filterConfig) throws ServletException {System.out.println("HttpFilter  init");Filter.super.init(filterConfig);}@Overridepublic void doFilter(ServletRequest request, ServletResponse response, FilterChain chain)throws IOException, ServletException {System.out.println("HttpFilter  doFilter begin");HttpServletRequest req =(HttpServletRequest) request;HttpServletResponse res =(HttpServletResponse) response;System.out.println("HttpFilter name:" + request.getParameter("name"));// 将请求转发给过滤器链上下一个对象。这里的下一个指的是下一个filter,如果没有filter那就是请求的资源。chain.doFilter(request, response);System.out.println("HttpFilter  doFilter end");}@Overridepublic void destroy() {System.out.println("HttpFilter  destroy");Filter.super.destroy();}
}
在配置类中注册该过滤器
@Configuration
public class FilterConfig {@Beanpublic FilterRegistrationBean<HttpFilter> httpFilter(){FilterRegistrationBean<HttpFilter> filterRegistrationBean = new FilterRegistrationBean<HttpFilter>();// 设置filterfilterRegistrationBean.setFilter(new HttpFilter());// 拦截规则filterRegistrationBean.addUrlPatterns("/*");return filterRegistrationBean;}
}

InterceptorFilter 小结

  • Filter 的执行顺序在 Interceptor 之前
  • Interceptor 是基于 Java 的反射机制,而过滤器 Filter 是基于函数回调
  • Filter 能做的事情,Interceptor 都能做,而且可以在请求前,请求后执行,比较灵活

SpringBoot中Interceptor和Filter的使用相关推荐

  1. springboot中的拦截器interceptor和过滤器filter,多次获取request参数

    大家好,我是烤鸭:     这是一篇关于springboot的拦截器(interceptor)和过滤器(Filter). 先说一下过滤器和拦截器. 区别: 1. servlet请求,顺序:Filter ...

  2. SpringBoot中AOP实现落地——Filter(过滤器)、Intercepter(拦截器)、Aspect(Spring AOP)

    文章目录 一.一切要从Servlet说起 1.1什么是Servlet 1.2为什么需要Servlet 1.3Servlet如何响应用户请求 1.4Servlet与Tomcat处理请求的流程 1.5Se ...

  3. SpringBoot中使用拦截器、servlet、过滤器Filter

    Spring Boot 使用拦截器步骤: 1. 创建类实现 HandlerInterceptor 接口 package com.dongmu.interceptor;import org.spring ...

  4. java filter注入,Spring-boot中Filter注入bean

    Spring-boot中Filter注入bean 在spring中使用Filter的方式不用再多说,但是通常情况下我们在使用filter中都可能会注入部分配置的类或者部分具有特殊功能的业务类. 在这种 ...

  5. SpringBoot中如何配置使用过滤器(Filter)呢?

    转自: SpringBoot中如何配置使用过滤器(Filter)呢? 下文笔者讲述springboot中配置过滤器的方法分享,如下所示 实现思路:1.定义filter2.将filter注册进sprin ...

  6. 【小家Spring】SpringBoot中使用Servlet、Filter、Listener三大组件的三种方式以及原理剖析

    每篇一句 要么就安逸的穷,要么就拼命的干 前提概要 web开发使用Controller基本能解决大部分的需求,但是有时候我们也需要使用Servlet,因为相对于拦截和监听来说,有时候原生的还是比较好用 ...

  7. springboot中添加Filter的方法

    springboot中创建Filter有四种方法,具体如下 第一种 @WebFilter(filterName = "myFilter",urlPatterns = "/ ...

  8. SpringBoot mybatis Interceptor分页实现

    环境准备 什么是拦截器 为什么要这样写 具体实现 什么是拦截器 SpringBoot mybatis interceptor拦截器是你在执行SQL语句之前对执行的SQL语句进行修改 分页的原理是通过拦 ...

  9. SpringBoot之Interceptor拦截器注入使用

    相关文章: SpringBoot 之AOP切面的使用 SpringBoot之Listener注册到Spring容器中的多种方法 SpringBoot之Filter过滤器的实现及排序问题 SpringB ...

  10. CGlib、Enhancer、ProxyFactory在springboot中的实现动态代理

    本人博客原地址:CGlib.Enhancer.ProxyFactory在springboot中的实现动态代理 创作时间:2019.06.27 11:38:35 基于springboot2.1.4 在s ...

最新文章

  1. python类的空间问题及类之间的关系
  2. 做「容量预估」可没有true和false
  3. [vue] v-on可以绑定多个方法吗?
  4. MySQL流浪记(七)—— MySQL删除表数据
  5. 【Computer Organization笔记04】ALU的基本功能,1位ALU,位数扩展以及功能扩展
  6. Openlayer:学习笔记之Source和Layer
  7. response 画验证码
  8. windows定时截屏小工具
  9. 分享15款堪称神器却鲜为人知的软件和网站
  10. 【干货】ubuntu18.04+win7双系统+双硬盘安装总结
  11. 当下的力量(解读版)
  12. LigerUi中表(Grid)控件的相关属性笔记(持续添加中)
  13. 实时音视频 质量测试
  14. TimestampUtil时间处理工具类
  15. 项目要求完成杀毒软件,可是为什么网上关于杀毒软件的资料那么少啊
  16. 航天环宇提交招股书上会稿:计划募资6亿元,控股股东为李完小
  17. Hadoop安装与部署
  18. Mysql - 对所有员工的薪水按照salary进行按照1-N的排名
  19. ipad无法充电怎么办_ipad无法充电无法开机怎么办 详细解决方法介绍【图文】
  20. 上海计算机专科学院分数线,分数线|上海

热门文章

  1. 容器技术Docker K8s 9 容器服务ACK应用场景
  2. 为什么必须在主线程操作UI
  3. CTR介绍,数据集往往为表格形式,训练集使用历史的日志数据,然后进行特征归一化、离散化和特征哈希等操作,最终一条训练集为一行多列的二分类任务。
  4. 动脑学院_张晨到梅州职业技术学院施工现场调研:强力加快进度,确保项目如期建成...
  5. 深度学习笔记(五):LSTM
  6. 离散数学复习--第一章:命题逻辑
  7. java基础学习(7)浅析final,private,public,protected,static等关键以及它们的区别的联系
  8. 计算机组成原理完整学习笔记(四):输入输出系统
  9. 「快手极速版」榜 App Store 总榜第一
  10. h3c交换机堆叠(IRF)配置三步完成