一文搞懂过滤器、拦截器的区别

过滤器(Filter)

过滤器的实现

直接实现filter接口,也可以通过@WebFilter注解实现对特定的URL拦截
package com.example.filter;


import org.springframework.stereotype.Component;

import javax.servlet.*;
import java.io.IOException;

/**
 * @author 米斯特白
 */
@Component
public class MyFilter implements Filter {
    /**
     * 该方法在容器启动初始化过滤器时被调用,
     * 它在 Filter 的整个生命周期只会被调用一次。
     *「注意」:这个方法必须执行成功,否则过滤器会不起作用。
     * @param filterConfig
     * @throws ServletException
     */
    @Override
    public void init(FilterConfig filterConfig) throws ServletException {
        System.out.println("Filter 前置");
    }

    /**
     * 容器中的每一次请求都会调用该方法, FilterChain 用来调用下一个过滤器 Filter。
     * @param servletRequest
     * @param servletResponse
     * @param filterChain
     * @throws IOException
     * @throws ServletException
     */
    @Override
    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse,
                         FilterChain filterChain) throws IOException, ServletException {
        System.out.println("Filter 处理中");
        filterChain.doFilter(servletRequest, servletResponse);
    }

    /**
     * 当容器销毁 过滤器实例时调用该方法,一般在方法中销毁或关闭资源,
     * 在过滤器 Filter 的整个生命周期也只会被调用一次
     */
    @Override
    public void destroy() {
        System.out.println("Filter 后置");
    }
}

拦截器 (Interceptor)

一个应用中可以同时存在多个拦截器Interceptor, 一个请求也可以触发多个拦截器,
而每个拦截器的调用会依据它的声明顺序依次执行。

拦截器实现

package com.example.filter;

import org.springframework.stereotype.Component;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 *
 *
 * @author 米斯特白
 */
@Component
public class MyInterceptor implements HandlerInterceptor {

    /**
     * 在请求处理之前进行调用。
     *【注意】:如果该方法的返回值是false,视为当前请求结束,不仅自身的拦截器会失效,还会导致其他拦截器也不再执行。
     * @param request
     * @param response
     * @param handler
     * @return
     * @throws Exception
     */
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        System.out.println("Interceptor 前置");
        return true;
    }


    /**
     * 只有在preHandle()方法返回true时才会执行。会在controller中的方法调用之后,dispatcherServlet返回视图渲染之前被调用。
     *【有意思的是】 postHandle()方法的调用顺序跟 preHandle()正好是相反的,先声明的拦截器preHandle() 方法先执行,
     * 而 postHandle方法反而会后执行。
     * @param request
     * @param response
     * @param handler
     * @param modelAndView
     * @throws Exception
     */
    @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
        System.out.println("Interceptor 处理中");
    }

    /**
     * 之后再preHandle()方法返回值为true时才会执行,在整个请求结束之后,DispatcherServlet渲染了对应的视图之后执行。
     * @param request
     * @param response
     * @param handler
     * @param ex
     * @throws Exception
     */
    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
        System.out.println("Interceptor 后置");
    }
}

拦截器配置

package com.example.config;

import com.example.filter.MyInterceptor;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.InterceptorRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;

/**
 * @author 米斯特白
 */
@Configuration
public class MyMvcConfig implements WebMvcConfigurer {
    /**
     * 配置拦截器
     * @param registry
     */
    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        registry.addInterceptor(new MyInterceptor()).addPathPatterns("/**");
    }
}

过滤器和拦截器都体现了AOP思想,都可以实现比如日志记录,登录权限等功能,但是二者的不同点也是比较多的。

过滤器和拦截器的区别

1.实现原理不同

过滤器是基于回调函数的
拦截器是基于Java的反射机制(动态代理)实现的
【重点】过滤器
在我们定义的filter中都会实现一个doFilter()方法,这个方法有一个filterChain参数,实际上它是
一个回调接口。
ApplicationFilterChain是它的一个实现类,这个实现类也有一个doFilter()方法就是回调方法。
ApplicationFilterChain能拿到我们自定义的filter类,其内部回调方法doFilter()里
会调用各个自定义的xxxFilter过滤器,并执行doFilter()方法。
而每个xxxFilter 会先执行自身的 doFilter() 过滤逻辑,最后在执行结束前会执行
filterChain.doFilter(servletRequest, servletResponse),
也就是回调ApplicationFilterChain的doFilter() 方法,以此循环执行实现函数回调。
public interface FilterChain {
    void doFilter(ServletRequest var1, ServletResponse var2) 
                                                 [图片上传中...(未命名文件.png-672b65-1653919111382-0)]
throws IOException, ServletException;
}
未命名文件.png

ApplicationFilterChain拿到我们自定义的filter,执行doFilter方法调用各个自定义的doFilter()方法。

而每个自定义的filter会先执行自己的doFilter()逻辑,在执行结束之前执行filterChain.dofilter(servletRequest, servletResponse),也就是回调ApplicationFilterChain的doFilter()方法,ApplicationFilterChain的获取下一个filter,继续循环执行。

2、使用范围不同

filter是servlet中的规范,也就是说filter的使用依赖于Tomcat等web容器,所以它只能在web程序中使用,
而拦截器(Intercepter)它是一个spring组件,并由spring容器管理、,并不依赖于Tomcat等容器,
是可以单独使用的。不仅在web程序中可以使用,在application,Swing等程序中也可以使用。

3、触发时机不同

image.png
过滤器filter是在请求容器之后,但是在进入servlet之前进行预处理,请求结束是在servlet处理完之后。
拦截器Interceptor是在请求进入servlet之后,在controller之前进行预处理,
controller中渲染了对应的视图之后请求结束。

4、拦截的请求范围不同
我们配置好了拦截器和过滤器,下边我们看一下他们的请求范围。

D:\developTool\jdk1.8\bin\java.exe -agentlib:jdwp=transport=dt_socket,address=127.0.0.1:64029,suspend=y,server=n -XX:TieredStopAtLevel=1 -noverify -Dspring.output.ansi.enabled=always -Dcom.sun.management.jmxremote -Dspring.jmx.enabled=true -Dspring.liveBeansView.mbeanDomain -Dspring.application.admin.enabled=true -javaagent:C:\Users\米斯特白\AppData\Local\Temp\captureAgentjars\debugger-agent.jar -Dfile.encoding=UTF-8 -classpath "D:\developTool\jdk1.8\jre\lib\charsets.jar;D:\developTool\jdk1.8\jre\lib\deploy.jar;D:\developTool\jdk1.8\jre\lib\ext\access-bridge-64.jar;D:\developTool\jdk1.8\jre\lib\ext\cldrdata.jar;D:\developTool\jdk1.8\jre\lib\ext\dnsns.jar;D:\developTool\jdk1.8\jre\lib\ext\jaccess.jar;D:\developTool\jdk1.8\jre\lib\ext\jfxrt.jar;D:\developTool\jdk1.8\jre\lib\ext\localedata.jar;D:\developTool\jdk1.8\jre\lib\ext\nashorn.jar;D:\developTool\jdk1.8\jre\lib\ext\sunec.jar;D:\developTool\jdk1.8\jre\lib\ext\sunjce_provider.jar;D:\developTool\jdk1.8\jre\lib\ext\sunmscapi.jar;D:\developTool\jdk1.8\jre\lib\ext\sunpkcs11.jar;D:\developTool\jdk1.8\jre\lib\ext\zipfs.jar;D:\developTool\jdk1.8\jre\lib\javaws.jar;D:\developTool\jdk1.8\jre\lib\jce.jar;D:\developTool\jdk1.8\jre\lib\jfr.jar;D:\developTool\jdk1.8\jre\lib\jfxswt.jar;D:\developTool\jdk1.8\jre\lib\jsse.jar;D:\developTool\jdk1.8\jre\lib\management-agent.jar;D:\developTool\jdk1.8\jre\lib\plugin.jar;D:\developTool\jdk1.8\jre\lib\resources.jar;D:\developTool\jdk1.8\jre\lib\rt.jar;F:\workspaces\springboot-redis\target\classes;D:\developTool\mavenRepository\.m2\repository\redis\clients\jedis\3.3.0\jedis-3.3.0.jar;D:\developTool\mavenRepository\.m2\repository\org\slf4j\slf4j-api\1.7.32\slf4j-api-1.7.32.jar;D:\developTool\mavenRepository\.m2\repository\org\apache\commons\commons-pool2\2.11.1\commons-pool2-2.11.1.jar;D:\developTool\mavenRepository\.m2\repository\com\alibaba\fastjson\1.2.78\fastjson-1.2.78.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\boot\spring-boot-starter-data-redis\2.6.1\spring-boot-starter-data-redis-2.6.1.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\boot\spring-boot-starter\2.6.1\spring-boot-starter-2.6.1.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\boot\spring-boot-starter-logging\2.6.1\spring-boot-starter-logging-2.6.1.jar;D:\developTool\mavenRepository\.m2\repository\ch\qos\logback\logback-classic\1.2.7\logback-classic-1.2.7.jar;D:\developTool\mavenRepository\.m2\repository\ch\qos\logback\logback-core\1.2.7\logback-core-1.2.7.jar;D:\developTool\mavenRepository\.m2\repository\org\apache\logging\log4j\log4j-to-slf4j\2.14.1\log4j-to-slf4j-2.14.1.jar;D:\developTool\mavenRepository\.m2\repository\org\apache\logging\log4j\log4j-api\2.14.1\log4j-api-2.14.1.jar;D:\developTool\mavenRepository\.m2\repository\org\slf4j\jul-to-slf4j\1.7.32\jul-to-slf4j-1.7.32.jar;D:\developTool\mavenRepository\.m2\repository\jakarta\annotation\jakarta.annotation-api\1.3.5\jakarta.annotation-api-1.3.5.jar;D:\developTool\mavenRepository\.m2\repository\org\yaml\snakeyaml\1.29\snakeyaml-1.29.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\data\spring-data-redis\2.6.0\spring-data-redis-2.6.0.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\data\spring-data-keyvalue\2.6.0\spring-data-keyvalue-2.6.0.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\data\spring-data-commons\2.6.0\spring-data-commons-2.6.0.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\spring-tx\5.3.13\spring-tx-5.3.13.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\spring-oxm\5.3.13\spring-oxm-5.3.13.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\spring-aop\5.3.13\spring-aop-5.3.13.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\spring-context-support\5.3.13\spring-context-support-5.3.13.jar;D:\developTool\mavenRepository\.m2\repository\io\lettuce\lettuce-core\6.1.5.RELEASE\lettuce-core-6.1.5.RELEASE.jar;D:\developTool\mavenRepository\.m2\repository\io\netty\netty-common\4.1.70.Final\netty-common-4.1.70.Final.jar;D:\developTool\mavenRepository\.m2\repository\io\netty\netty-handler\4.1.70.Final\netty-handler-4.1.70.Final.jar;D:\developTool\mavenRepository\.m2\repository\io\netty\netty-resolver\4.1.70.Final\netty-resolver-4.1.70.Final.jar;D:\developTool\mavenRepository\.m2\repository\io\netty\netty-buffer\4.1.70.Final\netty-buffer-4.1.70.Final.jar;D:\developTool\mavenRepository\.m2\repository\io\netty\netty-codec\4.1.70.Final\netty-codec-4.1.70.Final.jar;D:\developTool\mavenRepository\.m2\repository\io\netty\netty-transport\4.1.70.Final\netty-transport-4.1.70.Final.jar;D:\developTool\mavenRepository\.m2\repository\io\projectreactor\reactor-core\3.4.12\reactor-core-3.4.12.jar;D:\developTool\mavenRepository\.m2\repository\org\reactivestreams\reactive-streams\1.0.3\reactive-streams-1.0.3.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\boot\spring-boot-starter-web\2.6.1\spring-boot-starter-web-2.6.1.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\boot\spring-boot-starter-json\2.6.1\spring-boot-starter-json-2.6.1.jar;D:\developTool\mavenRepository\.m2\repository\com\fasterxml\jackson\core\jackson-databind\2.13.0\jackson-databind-2.13.0.jar;D:\developTool\mavenRepository\.m2\repository\com\fasterxml\jackson\core\jackson-annotations\2.13.0\jackson-annotations-2.13.0.jar;D:\developTool\mavenRepository\.m2\repository\com\fasterxml\jackson\core\jackson-core\2.13.0\jackson-core-2.13.0.jar;D:\developTool\mavenRepository\.m2\repository\com\fasterxml\jackson\datatype\jackson-datatype-jdk8\2.13.0\jackson-datatype-jdk8-2.13.0.jar;D:\developTool\mavenRepository\.m2\repository\com\fasterxml\jackson\datatype\jackson-datatype-jsr310\2.13.0\jackson-datatype-jsr310-2.13.0.jar;D:\developTool\mavenRepository\.m2\repository\com\fasterxml\jackson\module\jackson-module-parameter-names\2.13.0\jackson-module-parameter-names-2.13.0.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\boot\spring-boot-starter-tomcat\2.6.1\spring-boot-starter-tomcat-2.6.1.jar;D:\developTool\mavenRepository\.m2\repository\org\apache\tomcat\embed\tomcat-embed-core\9.0.55\tomcat-embed-core-9.0.55.jar;D:\developTool\mavenRepository\.m2\repository\org\apache\tomcat\embed\tomcat-embed-el\9.0.55\tomcat-embed-el-9.0.55.jar;D:\developTool\mavenRepository\.m2\repository\org\apache\tomcat\embed\tomcat-embed-websocket\9.0.55\tomcat-embed-websocket-9.0.55.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\spring-web\5.3.13\spring-web-5.3.13.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\spring-beans\5.3.13\spring-beans-5.3.13.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\spring-webmvc\5.3.13\spring-webmvc-5.3.13.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\spring-context\5.3.13\spring-context-5.3.13.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\spring-expression\5.3.13\spring-expression-5.3.13.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\boot\spring-boot-devtools\2.6.1\spring-boot-devtools-2.6.1.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\boot\spring-boot\2.6.1\spring-boot-2.6.1.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\boot\spring-boot-autoconfigure\2.6.1\spring-boot-autoconfigure-2.6.1.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\boot\spring-boot-configuration-processor\2.6.1\spring-boot-configuration-processor-2.6.1.jar;D:\developTool\mavenRepository\.m2\repository\org\projectlombok\lombok\1.18.22\lombok-1.18.22.jar;D:\developTool\mavenRepository\.m2\repository\mysql\mysql-connector-java\8.0.16\mysql-connector-java-8.0.16.jar;D:\developTool\mavenRepository\.m2\repository\com\alibaba\druid\1.2.3\druid-1.2.3.jar;D:\developTool\mavenRepository\.m2\repository\javax\annotation\javax.annotation-api\1.3.2\javax.annotation-api-1.3.2.jar;D:\developTool\mavenRepository\.m2\repository\com\baomidou\mybatis-plus-boot-starter\3.4.2\mybatis-plus-boot-starter-3.4.2.jar;D:\developTool\mavenRepository\.m2\repository\com\baomidou\mybatis-plus\3.4.2\mybatis-plus-3.4.2.jar;D:\developTool\mavenRepository\.m2\repository\com\baomidou\mybatis-plus-extension\3.4.2\mybatis-plus-extension-3.4.2.jar;D:\developTool\mavenRepository\.m2\repository\com\baomidou\mybatis-plus-core\3.4.2\mybatis-plus-core-3.4.2.jar;D:\developTool\mavenRepository\.m2\repository\com\baomidou\mybatis-plus-annotation\3.4.2\mybatis-plus-annotation-3.4.2.jar;D:\developTool\mavenRepository\.m2\repository\com\github\jsqlparser\jsqlparser\4.0\jsqlparser-4.0.jar;D:\developTool\mavenRepository\.m2\repository\org\mybatis\mybatis\3.5.6\mybatis-3.5.6.jar;D:\developTool\mavenRepository\.m2\repository\org\mybatis\mybatis-spring\2.0.5\mybatis-spring-2.0.5.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\boot\spring-boot-starter-jdbc\2.6.1\spring-boot-starter-jdbc-2.6.1.jar;D:\developTool\mavenRepository\.m2\repository\com\zaxxer\HikariCP\4.0.3\HikariCP-4.0.3.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\spring-jdbc\5.3.13\spring-jdbc-5.3.13.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\spring-core\5.3.13\spring-core-5.3.13.jar;D:\developTool\mavenRepository\.m2\repository\org\springframework\spring-jcl\5.3.13\spring-jcl-5.3.13.jar;D:\developTool\mavenRepository\.m2\repository\com\suyeer\mybatis-plus\3.2.0.6\mybatis-plus-3.2.0.6.jar;D:\developTool\mavenRepository\.m2\repository\org\eclipse\yasson\1.0.5\yasson-1.0.5.jar;D:\developTool\mavenRepository\.m2\repository\jakarta\json\bind\jakarta.json.bind-api\1.0.2\jakarta.json.bind-api-1.0.2.jar;D:\developTool\mavenRepository\.m2\repository\jakarta\json\jakarta.json-api\1.1.6\jakarta.json-api-1.1.6.jar;D:\developTool\mavenRepository\.m2\repository\org\glassfish\jakarta.json\1.1.5\jakarta.json-1.1.5-module.jar;D:\developTool\idea\IntelliJ IDEA 2019.2.3\lib\idea_rt.jar" com.example.SpringbootRedisApplication
Connected to the target VM, address: '127.0.0.1:64029', transport: 'socket'
14:24:22.822 [Thread-1] DEBUG org.springframework.boot.devtools.restart.classloader.RestartClassLoader - Created RestartClassLoader org.springframework.boot.devtools.restart.classloader.RestartClassLoader@609aea86

  .   ____          _            __ _ _
 /\\ / ___'_ __ _ _(_)_ __  __ _ \ \ \ \
( ( )\___ | '_ | '_| | '_ \/ _` | \ \ \ \
 \\/  ___)| |_)| | | | | || (_| |  ) ) ) )
  '  |____| .__|_| |_|_| |_\__, | / / / /
 =========|_|==============|___/=/_/_/_/
 :: Spring Boot ::                (v2.6.1)

2022-05-30 14:24:23.327  INFO 16376 --- [  restartedMain] com.example.SpringbootRedisApplication   : Starting SpringbootRedisApplication using Java 1.8.0_281 on 米斯特白 with PID 16376 (F:\workspaces\springboot-redis\target\classes started by 米斯特白 in F:\workspaces\springboot-redis)
2022-05-30 14:24:23.331  INFO 16376 --- [  restartedMain] com.example.SpringbootRedisApplication   : No active profile set, falling back to default profiles: default
2022-05-30 14:24:23.387  INFO 16376 --- [  restartedMain] .e.DevToolsPropertyDefaultsPostProcessor : Devtools property defaults active! Set 'spring.devtools.add-properties' to 'false' to disable
2022-05-30 14:24:23.388  INFO 16376 --- [  restartedMain] .e.DevToolsPropertyDefaultsPostProcessor : For additional web related logging consider setting the 'logging.level.web' property to 'DEBUG'
2022-05-30 14:24:24.113  INFO 16376 --- [  restartedMain] .s.d.r.c.RepositoryConfigurationDelegate : Multiple Spring Data modules found, entering strict repository configuration mode!
2022-05-30 14:24:24.115  INFO 16376 --- [  restartedMain] .s.d.r.c.RepositoryConfigurationDelegate : Bootstrapping Spring Data Redis repositories in DEFAULT mode.
2022-05-30 14:24:24.142  INFO 16376 --- [  restartedMain] .s.d.r.c.RepositoryConfigurationDelegate : Finished Spring Data repository scanning in 9 ms. Found 0 Redis repository interfaces.
2022-05-30 14:24:24.736  INFO 16376 --- [  restartedMain] o.s.b.w.embedded.tomcat.TomcatWebServer  : Tomcat initialized with port(s): 8080 (http)
2022-05-30 14:24:24.745  INFO 16376 --- [  restartedMain] o.a.coyote.http11.Http11NioProtocol      : Initializing ProtocolHandler ["http-nio-8080"]
2022-05-30 14:24:24.746  INFO 16376 --- [  restartedMain] o.apache.catalina.core.StandardService   : Starting service [Tomcat]
2022-05-30 14:24:24.746  INFO 16376 --- [  restartedMain] org.apache.catalina.core.StandardEngine  : Starting Servlet engine: [Apache Tomcat/9.0.55]
2022-05-30 14:24:24.840  INFO 16376 --- [  restartedMain] o.a.c.c.C.[Tomcat].[localhost].[/]       : Initializing Spring embedded WebApplicationContext
2022-05-30 14:24:24.840  INFO 16376 --- [  restartedMain] w.s.c.ServletWebServerApplicationContext : Root WebApplicationContext: initialization completed in 1452 ms
Filter 前置
 _ _   |_  _ _|_. ___ _ |    _ 
| | |\/|_)(_| | |_\  |_)||_|_\ 
     /               |         
                        3.4.2 
2022-05-30 14:24:26.103  WARN 16376 --- [  restartedMain] c.b.m.core.metadata.TableInfoHelper      : Can not find table primary key in Class: "com.example.pojo.User".
2022-05-30 14:24:26.847  INFO 16376 --- [  restartedMain] o.s.b.d.a.OptionalLiveReloadServer       : LiveReload server is running on port 35729
2022-05-30 14:24:26.862  INFO 16376 --- [  restartedMain] o.a.coyote.http11.Http11NioProtocol      : Starting ProtocolHandler ["http-nio-8080"]
2022-05-30 14:24:26.878  INFO 16376 --- [  restartedMain] o.s.b.w.embedded.tomcat.TomcatWebServer  : Tomcat started on port(s): 8080 (http) with context path ''
2022-05-30 14:24:26.898  INFO 16376 --- [  restartedMain] com.example.SpringbootRedisApplication   : Started SpringbootRedisApplication in 4.066 seconds (JVM running for 6.028)
2022-05-30 14:25:20.540  INFO 16376 --- [nio-8080-exec-1] o.a.c.c.C.[Tomcat].[localhost].[/]       : Initializing Spring DispatcherServlet 'dispatcherServlet'
2022-05-30 14:25:20.541  INFO 16376 --- [nio-8080-exec-1] o.s.web.servlet.DispatcherServlet        : Initializing Servlet 'dispatcherServlet'
2022-05-30 14:25:20.542  INFO 16376 --- [nio-8080-exec-1] o.s.web.servlet.DispatcherServlet        : Completed initialization in 1 ms
Filter 处理中
Interceptor 前置
Interceptor 处理中
Interceptor 后置

Process finished with exit code 130

我们发现,过滤器的init()方法,随着容器的启动进行了初始化。
然后,控制台打印的日志是:

Filter 处理中
Interceptor 前置
Interceptor 处理中
Interceptor 后置

5、注入Bean情况不同

在实际的业务场景中,应用到过滤器或拦截器,为处理业务逻辑难免会引入一些service服务。
在拦截器中注入service,发起请求测试一下 ,报错了,debug跟一下发现注入的service是Null
这是因为加载顺序导致的问题,拦截器加载的时间点在springcontext之前,而Bean又是由spring进行管理。

解决方案

@Configuration
public class MyMvcConfig implements WebMvcConfigurer {

    @Bean
    public MyInterceptor getMyInterceptor() {
        System.out.println("注入MyInterceptor到spring容器");
        return new MyInterceptor();
    }

    /**
     * 配置拦截器
     * @param registry
     */
    @Override
    public void addInterceptors(InterceptorRegistry registry) {
//        registry.addInterceptor(new MyInterceptor()).addPathPatterns("/**");
        registry.addInterceptor(getMyInterceptor()).addPathPatterns("/**");
    }
}

6、控制执行顺序不同

实际开发过程中,会出现多个过滤器或拦截器同时存在的情况,不过,有时我们希望某个过滤器或拦截器能优先执行,就涉及到它们的执行顺序。

过滤器用@Order注解控制执行顺序,通过@Order控制过滤器的级别,值越小级别越高越先执行。
拦截器默认的执行顺序,就是它的注册顺序,也可以通过Order手动设置控制,值越小越先执行。

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 218,036评论 6 506
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 93,046评论 3 395
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 164,411评论 0 354
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 58,622评论 1 293
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 67,661评论 6 392
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 51,521评论 1 304
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 40,288评论 3 418
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 39,200评论 0 276
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,644评论 1 314
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,837评论 3 336
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,953评论 1 348
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,673评论 5 346
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 41,281评论 3 329
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,889评论 0 22
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 33,011评论 1 269
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 48,119评论 3 370
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,901评论 2 355

推荐阅读更多精彩内容