Spring拦截器原理与实战详解

目录

拦截器:

拦截器与过滤器区别

下面是请求发出后的映射过程:

拦截器的入门案例:

第一步:创建一个java类,声明拦截器的bean,并实现HandlerInterceptor接口。

第二步:注册拦截器(不能只创建不使用吧!)

扫描的具体过程:

拦截器的参数;

拦截器链:


前言:当浏览器给我们发送一个请求的时候,请求先到达tomcat服务器,tomcat根据请求来确认这次请求该如何处理。拦截到了所有的请求,然后划分成了静态资源(html页面,CSS,JS等等),(tomcat服务器可以直接给我们)和动态资源,动态资源才是我们要处理的。动态资源不是直接进入到Cotroller层,而是先经过过滤器的筛选,不止一层,,之后才交给我们的处理器去做,中央控制器去会根据请求来判断进入到哪个controller层(将请求分发到具体的控制器当中)当controller执行完后,会返回给浏览器数据。而拦截器就是加在controller层前后的机制。

拦截器:

是一种动态拦截方法调用的机制,在SpringMvc中动态拦截控制器方法的执行。

作用:
++在指定的方法调用前后执行预先设定的代码++

++阻止原始方法的执行++

拦截器与过滤器区别

归属不同:Filter属于Servlet技术,Interceptor属于SpringMVc技术

拦截内容不同:Filter对所有访问进行增强,Interceptor仅针对SpringMVc的访问进行增强

原理:

拦截器拦截的是请求,可以在请求到达方法前后进行处理

Postman中localhost后面加的是接口地址,这个地址对应后端的一个方法

下面是请求发出后的映射过程:

复制代码
Postman请求: GET http://localhost:8080/api/users/info?id=1001
                    ↓
             DispatcherServlet (前端控制器)
                    ↓
         HandlerMapping (寻找对应的处理器)
                    ↓
             匹配到:@GetMapping("/info")
                    ↓
         HandlerAdapter (适配器,准备调用方法)
                    ↓
           UserController.getUserInfo(1001)
                    ↓
                返回响应

拦截器的入门案例:

第一步:创建一个java类,声明拦截器的bean,并实现HandlerInterceptor接口。

具体操作:

复制代码
// 使用 @Component 注解,将该类声明为一个Spring Bean
@Slf4j
@Component
public class LoginInterceptor implements HandlerInterceptor {

    // 在请求到达Controller之前执行
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        log.info("LoginInterceptor preHandle...");
        // 返回true表示放行,false表示拦截
        return true; 
    }

    // 在Controller执行之后,视图渲染之前执行
    @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
        log.info("LoginInterceptor postHandle...");
    }

    // 在整个请求完成之后执行
    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
        log.info("LoginInterceptor afterCompletion...");
    }
}

第二步:注册拦截器(不能只创建不使用吧!)

创建一个配置类,实现WebMvcconfigurer接口,并重写addInterceptor方法,将上一步定义的拦截器bean添加到InterceptorRegistry中。重点:这个配置类需要被Spring管理,使用@Configuration注解,

具体操作:

复制代码
// 使用 @Configuration 注解,声明这是一个配置类
@Configuration
public class WebConfig implements WebMvcConfigurer {

    // 自动注入我们定义好的拦截器Bean
    @Autowired
    private LoginInterceptor loginInterceptor;

    // 重写addInterceptors方法,进行注册
    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        // 注册拦截器,并配置拦截/放行的路径
        registry.addInterceptor(loginInterceptor) // 将拦截器Bean添加到注册中心
                .addPathPatterns("/**")          // 拦截所有请求路径
                .excludePathPatterns("/user/login", "/user/register"); // 放行登录和注册路径

扫描的具体过程:

Spring Boot在启动时,会扫描指定包(通常是主启动类所在包及其子包)下的所有类。它主要扫描两种东西:

  • 带有特定注解的类 :例如 @Component、@Configuration、@Service、@Controller 等。在我们的例子里,LoginInterceptor和WebConfig都被扫描到了。

  • 实现特定接口的类 :例如实现了WebMvcConfigurer接口的类。

  • 当扫描到LoginInterceptor上的@Component时,Spring容器会创建它的一个实例(一个Bean),并管理起来。

  • 当扫描到WebConfig上的@Configuration时,Spring会识别出它是一个配置类,并执行其内部定义好的配置逻辑,特别是重写的addInterceptors方法。

  • 在addInterceptors方法执行时,InterceptorRegistry(拦截器注册表)会拿到我们注入的loginInterceptor Bean,并将它注册到Spring MVC的内部拦截器链中。

最终,当一个请求(比如你在Postman中输入的地址)到达时,Spring MVC的分发器(DispatcherServlet)就会从这个拦截器链中依次调用匹配的拦截器,从而执行我们在LoginInterceptor中定义的preHandlepostHandle等逻辑。

拦截器的参数;

参数 使用场景 主要作用
request 所有方法 获取请求信息(头、参数、IP、URI等)
response preHandle, postHandle 控制响应(状态码、重定向、返回数据)
handler preHandle, postHandle, afterCompletion 获取目标方法信息(控制器、方法、注解)
modelAndView postHandle 操作模型数据和视图(仅页面请求)
exception afterCompletion 处理异常信息

拦截器链:

当配置多个拦截器时,就形成了拦截器链。

执行过程:

最后给大推荐如果您是计算机领域(AI / 大数据 / 网络 / 软件工程等)的研究者,近期有成果想投稿发表,这几个高认可度的国际会议可以参考(均支持 EI/SCOPUS 检索):

第七届计算机信息与大数据应用会议:

https://ais.cn/u/QnaAJz

第九届先进算法与控制工程会议:

https://ais.cn/u/BFfyuq

相关推荐
vsropy28 分钟前
Ubuntu网络图标消失问题/有网络问号
linux·运维·ubuntu
fofantasy29 分钟前
NSK LH12AN 微型导轨技术手册
运维·网络·数据库·经验分享·规格说明书
coderwu38 分钟前
Ubuntu 24.04 终端输入 openclaw config 提示未找到命令解决办法
linux·运维·ubuntu
一 乐1 小时前
家政服务管理系统|基于springboot + vue家政服务管理系统(源码+数据库+文档)
java·数据库·vue.js·spring boot·论文·毕设·家政服务管理系统
dxxt_yy1 小时前
千兆光/电口+OTDR一体——成都鼎讯 SZT-1000A 千兆以太网测试仪助力风电能源光缆管理
运维·服务器·能源
tedcloud1231 小时前
taste-skill部署教程:打造个性化AI推荐工作流
服务器·前端·人工智能·系统架构·edge
碳基硅坊2 小时前
Spring AI:把大模型接进 Spring 应用
java·人工智能·spring ai
黄毛火烧雪下2 小时前
Java 核心知识点总结(一)
java·开发语言
凡人叶枫3 小时前
Effective C++ 条款28:避免使用 handles 指向对象内部
linux·服务器·开发语言·c++·嵌入式开发
技术小结-李爽3 小时前
【工具】Maven的下载、安装、使用
java·maven