当前位置: 首页 > news >正文

SpringMVC 的 拦截器

Spring MVC 提供了一套拦截器(Interceptor)机制,主要用于处理 Web 请求到达控制器之前或响应离开控制器之后执行一些操作。拦截器可以用于执行预处理(如验证用户身份)和后处理(如清理资源或修改响应)。拦截器可以用来执行一系列的任务,如身份验证、权限检查、请求/响应处理、日志记录等。

1.Handler 拦截器

Handler 拦截器是 Spring MVC 中最常见的拦截器类型。 Handler 拦截器实现 HandlerInterceptor 接口。

该接口定义了三个方法:

  1. preHandle:

    • 方法签名: boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception;
    • 用途: 在控制器方法调用之前执行。
    • 返回值: 如果返回 true,则控制器方法将被调用;如果返回 false,则控制器方法不会被调用,并且后续的拦截器也不会被调用。
  2. postHandle:

    • 方法签名: void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception;
    • 用途: 在控制器方法调用之后执行,但在视图渲染之前。
    • 参数:
      • request: 当前请求。
      • response: 当前响应。
      • handler: 被调用的控制器实例。
      • modelAndView: 控制器方法返回的模型和视图。
  3. afterCompletion:

    • 方法签名: void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception;
    • 用途: 在整个请求完成后执行,无论是否出现异常。
    • 参数:
      • request: 当前请求。
      • response: 当前响应。
      • handler: 被调用的控制器实例。
      • ex: 如果在请求处理过程中出现了异常,则此参数为异常对象;否则为 null

2.实现示例

下面是一个简单的 Handler 拦截器示例:

import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;public class MyHandlerInterceptor implements HandlerInterceptor {@Overridepublic boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {System.out.println("Pre Handle: " + request.getMethod() + " " + request.getRequestURI());return true; // 继续处理请求}@Overridepublic void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {System.out.println("Post Handle: " + request.getRequestURI());}@Overridepublic void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {System.out.println("After Completion: " + request.getRequestURI());}
}

3.配置拦截器

要使拦截器生效,你需要将其注册到 Spring MVC 的配置中。这可以通过 XML 配置文件或 Java 配置类来实现。

3.1.XML 配置示例

<mvc:interceptors><bean class="com.example.MyHandlerInterceptor" />
</mvc:interceptors>

3.2.Java 配置示例

import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.InterceptorRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;@Configuration
public class WebConfig implements WebMvcConfigurer {@Overridepublic void addInterceptors(InterceptorRegistry registry) {registry.addInterceptor(new MyHandlerInterceptor()).addPathPatterns("/**") // 指定拦截器的应用路径.excludePathPatterns("/resources/**", "/static/**"); // 排除静态资源}
}

4.与过滤器Filter比较

Spring MVC 中的拦截器(Interceptor)和过滤器(Filter)都是处理 Web 请求的重要机制,但它们之间存在一些关键的区别。下面将详细比较这两种机制:

1. 概念区别

  • 过滤器 (Filter):

    • 过滤器是 Servlet 规范的一部分,因此它适用于所有基于 Servlet 的容器,包括 Spring MVC。
    • 过滤器可以在请求到达任何其他组件之前和响应发送给客户端之后执行。
    • 过滤器可以应用于整个 Web 应用程序,也可以针对特定 URL 模式。
  • 拦截器 (Interceptor):

    • 拦截器是 Spring MVC 特有的概念,它只能在 Spring MVC 上下文中使用。
    • 拦截器主要用于处理 HTTP 请求和响应的生命周期,但仅限于那些通过 Spring MVC DispatcherServlet 处理的请求。
    • 拦截器可以针对特定的控制器方法或一组控制器方法。

2. 生命周期

  • 过滤器 (Filter):

    • 过滤器在整个应用生命周期内只初始化一次,并且每个请求/响应都会经过过滤器链。
    • 过滤器可以实现 init()doFilter()destroy() 方法。
    • doFilter() 方法在每次请求时调用,而 init()destroy() 分别在容器初始化过滤器和销毁过滤器时调用。
  • 拦截器 (Interceptor):

    • 拦截器也只初始化一次,但它们仅在请求到达 Spring MVC DispatcherServlet 时生效。
    • 拦截器可以实现 preHandle()postHandle()afterCompletion() 方法。
    • preHandle() 在控制器方法之前调用,postHandle() 在控制器方法之后但视图渲染之前调用,afterCompletion() 在整个请求完成后调用。

3. 配置方式

  • 过滤器 (Filter):

    • 过滤器可以通过部署描述符(web.xml 文件)或 Java 配置类(通过 FilterRegistrationBean)来配置。
    • 过滤器需要指定 URL 模式,以确定哪些请求应通过该过滤器。
  • 拦截器 (Interceptor):

    • 拦截器可以通过 XML 配置文件或 Java 配置类来配置。
    • 拦截器可以针对特定的控制器方法或一组控制器方法,通过指定路径模式来配置。

4. 适用场景

  • 过滤器 (Filter):

    • 通常用于执行全局性的操作,如编码转换、登录验证、安全过滤等。
    • 适合在请求到达任何其他组件之前执行的操作,例如登录检查、安全过滤、压缩等。
  • 拦截器 (Interceptor):

    • 更侧重于与 Spring MVC 相关的功能,如权限检查、数据校验、日志记录等。
    • 适合在控制器方法之前或之后执行的操作,例如数据预处理、视图后处理、资源清理等。

相关文章:

SpringMVC 的 拦截器

Spring MVC 提供了一套拦截器&#xff08;Interceptor&#xff09;机制&#xff0c;主要用于处理 Web 请求到达控制器之前或响应离开控制器之后执行一些操作。拦截器可以用于执行预处理&#xff08;如验证用户身份&#xff09;和后处理&#xff08;如清理资源或修改响应&#x…...

Redisson可重入锁原理(基于黑马视频总结,保姆级)

上一篇文章我们基于redis的set nx ex 命令以及Lua脚本实现了基本的分布式锁&#xff0c;但是还存在一下几点问题。于是又引出了redisson。 为什么基于SETNX的分布式锁无法实现可重入 先在method1中获取锁&#xff0c;获取成功后又调用method2&#xff0c;而method2内部也会获取…...

Ubuntu 安装 Watt-Toolkit

一、下载 Watt-Toolkit 下载Watt-Toolkithttps://steampp.net/download 二、设置 Watt-Toolkit 打开 Watt-Toolkit&#xff0c;点击 “网络加速→加速设置&#xff0c;打开证书文件夹” &#xff0c;当前证书路径为&#xff1a;/home/yammie/.local/share/Steam/Plugins/Acc…...

python中的省略号(...)

下面对python学习中遇到的省略号做个总结 # 1. 前言 在Python中&#xff0c;一切皆对象&#xff0c;...也是对象&#xff0c;它和对象Ellipsis是等价的。对象...和Ellipsis的类型都是ellipsis&#xff0c;代码示例如下。 print(Ellipsis) # 输出&#xff1a;Ellipsis print(…...

第129天:内网安全-横向移动WmiSmbCrackMapExecProxyChainsImpacket

这里这个环境继续上一篇文章搭建的环境 案例一&#xff1a; 域横向移动-WMI-自带&命令&套件&插件 首先上线win2008 首先提权到system权限 wmic是windows自带的命令&#xff0c;可以通过135端口进行连接利用&#xff0c;只支持明文方式&#xff0c;优点是不用上传别…...

ChatGPT教我将MySQL中where find_in_set改成PostgreSQL支持的写法

问题 之前使用Mybatis&#xff0c;在MySQL中使用如下SQL语句没有问题&#xff1a; SELECT * FROM dept WHERE find_in_set(5,dept_parent);现在切换到PostgreSQL,发现find_in_set函数不能使用。 解决 SELECT * FROM dept WHERE 5 ANY(string_to_array(dept_parent, ,));总…...

Python命令模式:掌控你的代码指令

Python命令模式&#xff1a;掌控你的代码指令 在软件工程的浩瀚海洋中&#xff0c;命令模式&#xff08;Command Pattern&#xff09;是一盏指引航向的明灯&#xff0c;它将请求或操作封装成对象&#xff0c;从而让代码更加灵活、可扩展。本文将深入探讨Python中的命令模式&am…...

【物联网】(防水篇)电子产品 IPX7 防水级别测试的具体流程

电子产品 IPX7 防水级别测试的具体流程 1. 准备工作&#xff1a; - 准备一个足够大的浸水箱&#xff0c;确保水深至少为 1 米&#xff0c;以满足 IPX7 测试的标准要求。 - 将水温控制在标准温度范围内&#xff0c;通常在 15-35 摄氏度之间&#xff0c;以模拟正常使用环境。 2…...

Redis 实现消息队列

Redis 实现消息队列 文章目录 Redis 实现消息队列导引1. 基于List结构的消息队列2. 基于PubSub的消息队列3. 基于Stream的消息队列(推荐)3.1 XADD3.2 XREAD3.3 XGROUP 导引 消息队列(Message Queue)&#xff0c;从概念上来理解就是用来存放消息的队列&#xff0c;最简单的消息…...

模板初阶(详解)

一、泛型编程 为了引出模板&#xff0c;我们来看下面代码&#xff0c;比如要实现不同类型的交换函数&#xff0c;如下&#xff1a; void Swap(int& a, int& b) {int c a;a b;b c; } void Swap(char& a, char& b) {char c a;a b;b c; } void Swap(doubl…...

对称加密算法解析:DES、AES及其在`pycryptodome` 和 `crypto-js` 模块中的应用

&#x1f4da; 对称加密算法解析&#xff1a;DES、AES及其在pycryptodome 和 crypto-js 模块中的应用 &#x1f5dd;️ DES 算法 算法原理 数据加密标准&#xff08;DES&#xff09;是一种对称密钥加密算法&#xff0c;用于保护数据的安全。DES 使用一个 56 位的密钥进行加密…...

C++设计模式(代理模式)

1. 电话虫 在海贼中&#xff0c;有一种神奇的通信工具叫做电话虫&#xff08;Den Den Mushi&#xff09;&#xff0c;外形如蜗牛&#xff0c;身上带有斑点或条纹或通体纯色&#xff0c;壳顶上有对讲机或按键&#xff0c;不接通时会睡觉&#xff0c;接通时会惊醒&#xff0c;并发…...

Linux系统驱动(十三)Linux内核定时器

文章目录 一、内核定时器原理二、定时器API三、使用定时器让LED灯闪烁四、使用定时器对按键进行消抖 一、内核定时器原理 内核当前时间通过jiffies获取&#xff0c;它是内核时钟节拍数&#xff0c;在linux内核启动的时候&#xff0c;jiffies开始&#xff08;按照一定频率&…...

Visual Studio 调试时加载符号慢

什么是调试符号 编译程序时生成的一组特殊字符&#xff0c;并包含有关变量和函数在生成的二进制文件中的位置以及其他服务信息的信息。 该数据集可用于逐步调试程序或检查第三方代码。 调试符号可以添加到可执行文件或库中&#xff0c;但是大多数现代编译器将它们存储为单独的…...

Spring Cloud Config:动态配置的魔法师

Spring Cloud Config&#xff1a;动态配置的魔法师 在微服务架构的浩瀚星海中&#xff0c;配置管理如同一颗璀璨的星辰&#xff0c;而Spring Cloud Config则是那颗能够实现配置信息集中管理和动态刷新的魔法星。本文将深入探索Spring Cloud Config的奥秘&#xff0c;揭示如何通…...

Webpack入门基础知识及案例

webpack相信大家都已经不陌生了&#xff0c;应用程序的静态模块打包工具。前面我们总结了vue&#xff0c;react入门基础知识&#xff0c;也分别做了vue3的实战小案例&#xff0c;react的实战案例&#xff0c;那么我们如何使用webpack对项目进行模块化打包呢&#xff1f; 话不多…...

对中国人工智能与国外人工智能的思考

作为一名语文老师&#xff0c;我在教育的领域中见证着时代的变迁&#xff0c;也关注着科技的发展&#xff0c;尤其是人工智能这一前沿领域。当我们将目光投向中国人工智能与国外人工智能的发展时&#xff0c;心中不禁涌起诸多思考。 中国的人工智能近年来犹如一颗璀璨的新星&am…...

【debian系统arm架构安装docker】且换源后依旧不行就离线导入镜像

安装docker 在Debian系统上安装Docker并使用阿里云的镜像源可以通过以下步骤完成 1.更新软件包索引 前置如果需要更换源的请移步 : 初始化配置(自动连wifi,自动开启SSH)换清华源,远程桌面连接 sudo apt-get update2.安装必要的软件包以允许apt通过HTTPS使用仓库 sudo apt-get …...

Readwise 官方 Obsidian 插件使用

Readwise 官方 Obsidian 插件简介 Obsidian 中的 Readwise 注释示例 阅读已经发布了官方插件来导入你的 Readwise 数据Obsidian 。如果你还没有使用过 Readwise&#xff0c;那么值得一看。Readwise 是我最喜欢的 应用之一。我每天都在用它。因此&#xff0c;将这些数据自动导…...

A. A+B Again?

time limit per test 1 second memory limit per test 256 megabytes Given a two-digit positive integer nn, find the sum of its digits. Input The first line contains an integer tt (1≤t≤901≤t≤90) — the number of test cases. The only line of each tes…...

pr样机模板视频素材|城市户外高速路广告牌视频样机

https://prmuban.com/40369.html pr样机素材&#xff0c;全高清实景城市户外高速路广告牌视频样机模板&#xff0c;适合宣传视频制作。 主要特点&#xff1a; Adobe Premiere Pro 2024 全高清分辨率&#xff08;19201080&#xff09; 易于使用 快速渲染 无需插件 预览中使用的…...

谷歌大中华区总裁:所有企业都在问这个问题

中国开发者对于出海的热情&#xff0c;令Google大中华区总裁陈俊廷感慨。2024 Google I/O Connect&#xff08;2024Google开发者大会&#xff09;期间&#xff0c;他在接受第一财经记者独家采访时提到一个细节&#xff1a;早上7:30&#xff0c;他来到会场时&#xff0c;人们已经…...

GPT-4o:AI视觉识别的革命性飞跃

在AI的宏伟叙事中&#xff0c;图像识别技术始终扮演着关键角色。随着技术的不断演进&#xff0c;AI的视界已超越了简单的图像内容识别&#xff0c;它现在能够将视觉信息转化为引人入胜的文字描述。OpenAI最新力作——GPT-4o模型&#xff0c;以其卓越的多模态理解能力&#xff0…...

将电脑打造成私人网盘,支持外网访问之详细操作教程

你想过把自己电脑打造成随时随地访问的网盘吗&#xff1f;就是那种拥有一个属于自己的影音库&#xff0c;不用担心被和谐&#xff0c;随时可以登录访问电脑上的各种文件&#xff0c;相比传统网盘省心又安全。 使用Everything和节点小宝将电脑搭建成私人网盘&#xff0c;可以实现…...

spring同一个接口如何分页实现主表或主+联表group by查询

1 需求背景 我们的上游系统想要知道主表的记录关联子表所有记录中是否有一条满足特定的条件&#xff0c;如果有满足的就返回主表中的id。比如品牌brand主表中id为10的记录&#xff0c;在子表brand_rel中有id为1&#xff0c;2&#xff0c;3&#xff0c;4的这四个记录&#xff0…...

SpringDataJpa源码分析

我们在定义Repository的时候通常定义的时一个接口&#xff0c;而并没有去实现这个接口&#xff0c;那么Jpa是如何让开发者无需自己实现接口就可以使用Repository去操作数据库&#xff1f; 动态代理&#xff01;&#xff01;&#xff01; Repository原理 试想一下JPA是如何做的…...

卷积神经网络 - 卷积神经网络与深度学习的历史篇

序言 卷积神经网络&#xff08; Convolutional Neural Networks, CNN \text{Convolutional Neural Networks, CNN} Convolutional Neural Networks, CNN&#xff09;与深度学习作为人工智能领域的两大重要分支&#xff0c;其发展历程充满了探索与突破。深度学习&#xff0c;作…...

初识 Floodfall 算法

文章目录 **一、Floodfall 算法的概述****二、深度优先搜索&#xff08;DFS&#xff09;和广度优先搜索&#xff08;BFS&#xff09;在 Floodfall 算法中的应用****三、算法的基本原理****四、应用场景** 一、Floodfall 算法的概述 Floodfall 算法通常用于解决与区域填充、图的…...

[Linux] LVM挂载的硬盘重启就掉的问题解决

问题&#xff1a;系统重启后挂在逻辑卷的盘会掉&#xff08;必现&#xff09; 环境&#xff1a;SUSE Linux 11 SP4 原因&#xff1a;boot.lvm是关闭的 解决&#xff1a;boot.lvm设置开启 参考资料&#xff1a; linux下lvm状态Not avaliable问题排查及处理(常见Suse操作系统…...

YOLOv8改进 | 主干网络 | 用EfficientNet卷积替换backbone【教程+代码 】

秋招面试专栏推荐 :深度学习算法工程师面试问题总结【百面算法工程师】——点击即可跳转 💡💡💡本专栏所有程序均经过测试,可成功执行💡💡💡 专栏目录 :《YOLOv8改进有效涨点》专栏介绍 & 专栏目录 | 目前已有80+篇内容,内含各种Head检测头、损失函数Loss、…...