列举一下Spring MVC都有哪些拦截器配置类,按调用该顺序,逐个详细讲解功能及使用(DeepSeek)

Spring MVC 拦截器配置类详解(按调用顺序)
Spring MVC 提供了多种拦截器配置类和接口,以下是按调用顺序排列的详细说明:

1. HandlerInterceptor 接口

调用顺序:最先执行

功能:

核心拦截器接口,定义了三个拦截点:

  • preHandle - 处理器执行前
  • postHandle - 处理器执行后,视图渲染前
  • afterCompletion - 请求完成后

使用示例:

public class LoggingInterceptor implements HandlerInterceptor {
    
    @Override
    public boolean preHandle(HttpServletRequest request, 
                           HttpServletResponse response, 
                           Object handler) {
        log.info("请求开始: " + request.getRequestURI());
        return true;
    }
    
    @Override
    public void postHandle(HttpServletRequest request, 
                          HttpServletResponse response, 
                          Object handler, 
                          ModelAndView modelAndView) {
        log.info("请求处理完成: " + request.getRequestURI());
    }
    
    @Override
    public void afterCompletion(HttpServletRequest request, 
                               HttpServletResponse response, 
                               Object handler, 
                               Exception ex) {
        log.info("请求结束: " + request.getRequestURI());
    }
}

2. HandlerInterceptorAdapter(已废弃)

调用顺序:同 HandlerInterceptor

功能:

HandlerInterceptor 的适配器类(Spring 5.3+ 已废弃)

提供空实现,只需覆盖需要的方法

替代方案:

// 直接实现 HandlerInterceptor 接口
public class MyInterceptor implements HandlerInterceptor {
    // 使用 default 方法可以不实现所有方法
}

3. AsyncHandlerInterceptor 接口

调用顺序:在普通 HandlerInterceptor 之后

功能:

扩展 HandlerInterceptor,增加异步请求处理支持

新增方法:

afterConcurrentHandlingStarted - 当处理程序开始异步执行时调用

使用场景:

public class AsyncInterceptor implements AsyncHandlerInterceptor {
    
    @Override
    public void afterConcurrentHandlingStarted(HttpServletRequest request, 
                                             HttpServletResponse response, 
                                             Object handler) {
        // 异步请求开始时调用
        log.info("异步请求开始: " + request.getRequestURI());
    }
}

4. WebRequestInterceptor 接口

调用顺序:在 HandlerInterceptor 之后

功能:

提供更高级的 Web 请求抽象

不同于 HandlerInterceptor,它不依赖 Servlet API

方法:

preHandle(WebRequest request)

postHandle(WebRequest request, ModelMap model)

afterCompletion(WebRequest request, Exception ex)

使用示例:

public class WebRequestLogInterceptor implements WebRequestInterceptor {
    
    @Override
    public void preHandle(WebRequest request) throws Exception {
        log.info("WebRequest预处理: " + request.getContextPath());
    }
    
    @Override
    public void postHandle(WebRequest request, ModelMap model) throws Exception {
        if (model != null) {
            log.info("模型数据: " + model);
        }
    }
    
    @Override
    public void afterCompletion(WebRequest request, Exception ex) throws Exception {
        if (ex != null) {
            log.error("请求异常", ex);
        }
    }
}

5. MappedInterceptor 类

调用顺序:最后执行(但内部拦截器按注册顺序)

功能:

包装拦截器并添加路径匹配功能

可以指定包含路径和排除路径

配置方式:

@Configuration
public class WebConfig implements WebMvcConfigurer {
    
    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        registry.addInterceptor(new LoggingInterceptor())
                .addPathPatterns("/api/**")
                .excludePathPatterns("/api/public/**");
        
        // 等同于
        MappedInterceptor mappedInterceptor = new MappedInterceptor(
            new String[] {"/api/**"}, 
            new String[] {"/api/public/**"}, 
            new LoggingInterceptor());
        registry.addInterceptor(mappedInterceptor);
    }
}

6. InterceptorRegistry 类

调用顺序:管理所有拦截器的执行顺序

功能:

用于注册和排序拦截器

可以通过 order() 方法指定顺序

配置示例:

@Configuration
public class WebConfig implements WebMvcConfigurer {
    
    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        // 按添加顺序执行,除非指定order
        registry.addInterceptor(new SecurityInterceptor()).order(1);
        registry.addInterceptor(new LoggingInterceptor()).order(2);
        registry.addInterceptor(new PerformanceInterceptor()).order(3);
    }
}

7. Servlet API 原生过滤器 (Filter)

调用顺序:在 Spring 拦截器之前执行

功能:

虽然不属于 Spring MVC 拦截器,但常与拦截器配合使用

更底层的 Servlet 规范实现

与拦截器的区别:

特性 Filter Spring 拦截器
规范 Servlet规范 Spring 特有
执行时机 更早(在DispatcherServlet之前) 在DispatcherServlet之后
访问对象 ServletRequest/Response HttpServletRequest/Response
依赖 不依赖Spring 需要Spring环境

配置示例:

@Bean
public FilterRegistrationBean<MyFilter> myFilter() {
    FilterRegistrationBean<MyFilter> registration = new FilterRegistrationBean<>();
    registration.setFilter(new MyFilter());
    registration.addUrlPatterns("/*");
    registration.setOrder(Ordered.HIGHEST_PRECEDENCE); // 最高优先级
    return registration;
}

完整执行顺序总结

  1. Servlet Filter (如果有多个,按order顺序)
  2. HandlerInterceptor.preHandle (按注册顺序)
  3. Controller方法执行
  4. HandlerInterceptor.postHandle (按注册逆序)
  5. 视图渲染
  6. HandlerInterceptor.afterCompletion (按注册逆序)
  7. 异步请求特有:AsyncHandlerInterceptor.afterConcurrentHandlingStarted

最佳实践建议

安全相关 :使用Filter或高order值的拦截器
日志记录:使用低order值的拦截器
性能监控:使用preHandle和afterCompletion计算耗时
API版本控制:使用preHandle处理版本头
参数预处理:使用WebRequestInterceptor

通过合理组合这些拦截器组件,可以实现强大的横切关注点处理能力,同时保持业务代码的整洁性。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容