锋盈数科-知识库 Logo
首页
软件开发
计算机基础
Hello Halo
新手必读
关于本知识库
登录 →
锋盈数科-知识库 Logo
首页 软件开发 计算机基础 Hello Halo 新手必读 关于本知识库
登录
  1. 首页
  2. 软件开发
  3. JAVA
  4. 全面了解SpringBoot拦截器

全面了解SpringBoot拦截器

0
  • JAVA
  • 发布于 2024-08-09
  • 0 次阅读
黄健
黄健

本文由 简悦 SimpRead 转码, 原文地址 blog.csdn.net

在本文中,我们将详细介绍 SpringBoot 中的拦截器,包括拦截器的概念、作用、实现方式、执行顺序、生命周期以及高级应用。最后,我们还将探讨拦截器的性能优化策略和常见问题。

  1. 拦截器的概念和作用

1.1 什么是拦截器

拦截器(Interceptor)是一种特殊的组件,它可以在请求处理的过程中对请求和响应进行拦截和处理。拦截器可以在请求到达目标处理器之前、处理器处理请求之后以及视图渲染之前执行特定的操作。拦截器的主要目的是在不修改原有代码的情况下,实现对请求和响应的统一处理。

1.2 拦截器的作用

拦截器可以用于实现以下功能:

  1. 权限控制:拦截器可以在请求到达处理器之前进行权限验证,从而实现对不同用户的访问控制。
  2. 日志记录:拦截器可以在请求处理过程中记录请求和响应的详细信息,便于后期分析和调试。
  3. 接口幂等性校验:拦截器可以在请求到达处理器之前进行幂等性校验,防止重复提交。
  4. 数据校验:拦截器可以在请求到达处理器之前对请求数据进行校验,确保数据的合法性。
  5. 缓存处理:拦截器可以在请求处理之后对响应数据进行缓存,提高系统性能。

1.3 拦截器与过滤器的区别

拦截器和过滤器都可以实现对请求和响应的拦截和处理,但它们之间存在以下区别:

  1. 执行顺序:过滤器在拦截器之前执行,拦截器在处理器之前执行。

  2. 功能范围:过滤器可以对所有请求进行拦截,而拦截器只能对特定的请求进行拦截。

  3. 生命周期:过滤器由 Servlet 容器管理,拦截器由 Spring 容器管理。

  4. 使用场景:过滤器适用于对请求和响应的全局处理,拦截器适用于对特定请求的处理。

  5. SpringBoot 中的拦截器实现


2.1 实现 HandlerInterceptor 接口

要在 SpringBoot 中实现拦截器,首先需要创建一个类并实现 HandlerInterceptor 接口。HandlerInterceptor 接口包含以下三个方法:

  1. preHandle:在请求到达处理器之前执行,可以用于权限验证、数据校验等操作。如果返回 true,则继续执行后续操作;如果返回 false,则中断请求处理。
  2. postHandle:在处理器处理请求之后执行,可以用于日志记录、缓存处理等操作。
  3. afterCompletion:在视图渲染之后执行,可以用于资源清理等操作。

以下是一个简单的拦截器实现示例:

public class MyInterceptor implements HandlerInterceptor {

    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) {
        System.out.println("preHandle: " + request.getRequestURI());
        return true;
    }

    @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) {
        System.out.println("postHandle: " + request.getRequestURI());
    }

    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) {
        System.out.println("afterCompletion: " + request.getRequestURI());
    }
}

2.2 注册拦截器到 InterceptorRegistry

要让拦截器生效,需要将其注册到 InterceptorRegistry 中。这可以通过实现 WebMvcConfigurer 接口并重写 addInterceptors 方法来实现。以下是一个简单的注册示例:

@Configuration
public class WebMvcConfig implements WebMvcConfigurer {

    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        registry.addInterceptor(new MyInterceptor());
    }
}

2.3 配置拦截器的拦截规则

在注册拦截器时,可以通过 addPathPatterns 和 excludePathPatterns 方法来配置拦截器的拦截规则。addPathPatterns 方法用于指定需要拦截的请求路径,excludePathPatterns 方法用于指定不需要拦截的请求路径。以下是一个配置示例:

@Configuration
public class WebMvcConfig implements WebMvcConfigurer {

    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        registry.addInterceptor(new MyInterceptor())
                .addPathPatterns("/**")
                .excludePathPatterns("/login", "/register");
    }
}

在上述示例中,我们配置了拦截器拦截所有请求,但排除了登录和注册请求。

  1. 拦截器的执行顺序和生命周期

3.1 拦截器的执行顺序

当有多个拦截器时,它们的执行顺序取决于注册顺序。先注册的拦截器先执行,后注册的拦截器后执行。在请求处理过程中,拦截器的 preHandle 方法按注册顺序执行,而 postHandle 和 afterCompletion 方法按注册顺序的逆序执行。

3.2 拦截器的生命周期

拦截器的生命周期由 Spring 容器管理。当 Spring 容器启动时,拦截器会被实例化并初始化;当 Spring 容器关闭时,拦截器会被销毁。

3.3 多个拦截器的执行流程

当有多个拦截器时,它们的执行流程如下:

  1. 执行所有拦截器的 preHandle 方法,按注册顺序执行。如果某个拦截器的 preHandle 方法返回 false,则中断请求处理,直接执行已执行拦截器的 afterCompletion 方法。

  2. 执行处理器的处理方法。

  3. 执行所有拦截器的 postHandle 方法,按注册顺序的逆序执行。

  4. 渲染视图。

  5. 执行所有拦截器的 afterCompletion 方法,按注册顺序的逆序执行。

  6. 拦截器的高级应用


4.1 拦截器实现权限控制

拦截器可以在请求到达处理器之前进行权限验证,从而实现对不同用户的访问控制。以下是一个简单的权限控制示例:

public class AuthInterceptor implements HandlerInterceptor {

    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) {
        HttpSession session = request.getSession();
        User user = (User) session.getAttribute("user");
        if (user == null) {
            response.sendRedirect("/login");
            return false;
        }
        return true;
    }
}

在上述示例中,我们在 preHandle 方法中检查用户是否已登录,如果未登录,则重定向到登录页面并中断请求处理。

4.2 拦截器实现日志记录

拦截器可以在请求处理过程中记录请求和响应的详细信息,便于后期分析和调试。以下是一个简单的日志记录示例:

public class LogInterceptor implements HandlerInterceptor {

    private static final Logger logger = LoggerFactory.getLogger(LogInterceptor.class);

    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) {
        logger.info("Request URI: {}", request.getRequestURI());
        return true;
    }

    @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) {
        logger.info("Response status: {}", response.getStatus());
    }
}

在上述示例中,我们在 preHandle 方法中记录请求 URI,在 postHandle 方法中记录响应状态。

4.3 拦截器实现接口幂等性校验

拦截器可以在请求到达处理器之前进行幂等性校验,防止重复提交。以下是一个简单的幂等性校验示例:

public class IdempotentInterceptor implements HandlerInterceptor {

    private static final String IDEMPOTENT_TOKEN = "idempotentToken";

    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) {
        String token = request.getHeader(IDEMPOTENT_TOKEN);
        if (StringUtils.isEmpty(token)) {
            throw new RuntimeException("Idempotent token is missing");
        }
        if (!checkIdempotentToken(token)) {
            throw new RuntimeException("Duplicate request");
        }
        return true;
    }

    private boolean checkIdempotentToken(String token) {
        // Check the token in the cache or database
        // Return true if the token is valid, false otherwise
    }
}

在上述示例中,我们在 preHandle 方法中检查请求头中的幂等性令牌,如果令牌无效,则抛出异常并中断请求处理。

  1. 拦截器的性能优化和常见问题

5.1 拦截器性能优化策略

拦截器在请求处理过程中可能会影响系统性能,以下是一些性能优化策略:

  1. 减少拦截器数量:尽量将相关功能集中到一个拦截器中,避免创建过多的拦截器。
  2. 精确配置拦截规则:通过 addPathPatterns 和 excludePathPatterns 方法精确配置拦截规则,避免不必要的拦截。
  3. 使用异步处理:在拦截器中使用异步处理,避免阻塞请求处理过程。
  4. 使用缓存:在拦截器中使用缓存,减少对数据库或其他资源的访问。

5.2 拦截器的常见问题和解决方案

拦截器是一种用于处理请求和响应的中间件,它可以在请求到达目标处理器之前或响应返回客户端之前执行一些操作。然而,在实际使用过程中,我们可能会遇到一些问题,如拦截器不生效、执行顺序错误或影响性能等。接下来,我们将逐一分析这些问题的原因及解决方法。

  1. 拦截器不生效:拦截器不生效的可能原因有很多,其中最常见的包括拦截器未注册到 InterceptorRegistry、拦截规则配置错误等。为了解决这个问题,我们需要首先检查拦截器是否已经正确注册到 InterceptorRegistry 中,然后再检查拦截规则是否配置正确。如果发现问题,需要及时进行调整和修复。
  2. 拦截器执行顺序错误:拦截器执行顺序错误的主要原因是拦截器的注册顺序错误。在实际应用中,拦截器的执行顺序是根据它们在 InterceptorRegistry 中的注册顺序来决定的。因此,为了解决这个问题,我们需要调整拦截器在 InterceptorRegistry 中的注册顺序,确保它们按照预期的顺序执行。
  3. 拦截器影响性能:拦截器影响性能的主要原因是拦截器中的处理逻辑过于复杂或资源消耗过大。为了解决这个问题,我们需要对拦截器的处理逻辑进行优化,尽量减少不必要的计算和资源消耗。同时,我们还可以考虑使用一些性能监控工具,如 JProfiler 等,来对拦截器的性能进行实时监控和分析,从而找到性能瓶颈并进行优化。

拦截器在实际应用中可能会遇到一些问题,但只要我们能够深入了解其原理和机制,就可以找到合适的解决方案。

总结

本文详细介绍了 SpringBoot 中的拦截器,包括拦截器的概念、作用、实现方式、执行顺序、生命周期以及高级应用。我们还探讨了拦截器的性能优化策略和常见问题。希望本文能帮助您更好地理解和使用 SpringBoot 中的拦截器。

标签: #JAVA 991
相关文章

Spring 实现 3 种异步接口 2024-10-18 09:07

大家好,我是苏三~ 如何处理比较耗时的接口? 这题我熟,直接上异步接口,使用 Callable、WebAsyncTask 和 DeferredResult、CompletableFuture等均可实现。 但这些方法有局限性,处理结果仅返回单个值。在某些场景下,如果需要接口异步处理的同时,还持续不断地

重学SpringBoot3-集成Redis(五)之布隆过滤器 2024-10-08 11:24

更多SpringBoot3内容请关注我的专栏:《SpringBoot3》 期待您的点赞👍收藏⭐评论✍ 重学SpringBoot3-集成Redis(五)之布隆过滤器 1. 什么是布隆过滤器? * 基本概念 适用场景 2. 使用 Redis 实现布隆过滤器 * 项目依赖 Redis 配置

SpringBoot整合异步任务执行 2024-10-08 11:24

同步任务: 同步任务是在单线程中按顺序执行,每次只有一个任务在执行,不会引发线程安全和数据一致性等 并发问题 同步任务需要等待任务执行完成后才能执行下一个任务,无法同时处理多个任务,响应慢,影响用 户体验 异步任务: 异步任务是在多线程中同时执行,多个任务可以并发执行,同时处理多个请求,响应快,资源

springboot kafka多数据源,通过配置动态加载发送者和消费者 2024-10-08 11:24

前言 最近做项目,需要支持kafka多数据源,实际上我们也可以通过代码固定写死多套kafka集群逻辑,但是如果需要不修改代码扩展呢,因为kafka本身不处理额外逻辑,只是起到削峰,和数据的传递,那么就需要对架构做一定的设计了。 准备test kafka本身非常容易上手,如果我们需要单元测试,引入ja

SpringBoot 集成 Redis 2024-10-08 11:24

一:SpringBoot 集成 Redis ①Redis是一个 NoSQL(not only)数据库, 常作用缓存 Cache 使用。 ②Redis是一个中间件、是一个独立的服务器;常用的数据类型: string , hash ,set ,zset , list ③通过Redis客户端可以使用多种语

SpringBoot整合QQ邮箱 2024-10-08 11:24

SpringBoot可以通过导入依赖的方式集成多种技术,这当然少不了我们常用的邮箱,现在本章演示SpringBoot整合QQ邮箱发送邮件…. 下面按步骤进行: 1.获取QQ邮箱授权码 1.1 登录QQ邮箱 1.2 开启SMTP服务 找到下图中的SMTP服务区域,如果当前账号未开启的话自己手动开启。

目录

IT 外包服务商

  • 意见投递
  • zyf6619

软件开发应用

主菜单

  • 首页
  • 软件开发
  • 计算机基础
  • Hello Halo
  • 新手必读
  • 关于本知识库
Copyright © 2024 your company All Rights Reserved. Powered by Halo.