【SpringMVC】JSR 303与interceptor拦截器快速入门

目录

一、JSR303

1、什么是JSR 303?

2、为什么要使用JSR 303?

3、JSR 303常用注解

3.1、常用的JSR 303注解

3.2、@Validated与@Valid区别

3.2.1、@Validated

3.2.2、@Valid

3.2.3、区别

4、使用案例

4.1、导入依赖

4.2、配置校验规则

4.3、编写校验方法

4.4、前端代码

4.5、测试

二、interceptor拦截器

1、什么是拦截器?

2、为什么要使用拦截器?

3、拦截器与过滤器

 3.1、什么是过滤器(Filter)

3.2、拦截器与过滤器的区别

3.2.1、 过滤器(filter)

3.2.2、 拦截器(interceptor)

3.2.3、汇总

4、拦截器应用场景

5、使用案例

5.1、创建拦截器

5.2、配置拦截器

5.3、运行测试

5.4、拦截器工作原理

5.5、拦截器链

5.6、登录拦截实例

5.6.1、创建拦截器

5.6.2、配置拦截器

5.6.3、编写控制层

5.6.4、前端页面

5.6.5、测试

登入

登出


一、JSR303

1、什么是JSR 303?

JSR 303是Java规范请求(Java Specification Request)的缩写,意思是Java 规范提案。是指向JCP(Java Community Process)提出新增一个标准化技术规范的正式请求。任何人都可以提交JSR,以向Java平台增添新的API和服务。JSR已成为Java界的一个重要标准。 JSR-303 是JAVA EE 6 中的一项子规范,叫做Bean ValidationHibernate Validator Bean Validation 的参考实现 . Hibernate Validator 提供了 JSR 303 规范中所有内置 constraint(约束) 的实现,除此之外还有一些附加的 constraint。

它定义了一套用于Java Bean校验的标准。JSR 303使用注解的方式,在Spring MVC中被广泛应用于进行数据校验和验证。

验证数据是一项常见任务,它发生在从表示层到持久层的所有应用程序层中。通常在每一层都实现相同的验证逻辑,这既耗时又容易出错。为了避免重复这些验证,开发人员经常将验证逻辑直接捆绑到域模型中,将域类与验证代码混在一起,而验证代码实际上是关于类本身的元数据

2、为什么要使用JSR 303?

        在前端我们进行了数据校验,可是为什么我们还要做一篇,因为因为一点小失误我们的前端校验没有写好,但是有些人还是会绕过前端发送的请求(通过类似Postman这样的测试工具进行非常数据请求),传递一些错误的参数,这就会让我们的后端代码有大大的危险,所以我们一般都是前端一套校验,后端在一套校验,这样安全性就能够大大得到提升了。

所以我总和了JSR 303以下的好处:

  1. 提高代码的可维护性:通过在实体类中添加注解,可以清晰地标识出需要进行校验的字段和规则,使代码更易于理解和维护。
  2. 增强数据的完整性:根据定义的规则,可以自动校验输入数据的合法性,避免错误数据进入系统,保证数据的完整性和准确性。
  3. 减少重复代码:通过注解,可以在不同场景下重复使用相同的校验规则,减少编写重复代码的工作量。

3、JSR 303常用注解

3.1、常用的JSR 303注解

注解 说明 @Null 用于验证对象为null @NotNull 用于对象不能为null,无法查检长度为0的字符串 @NotBlank 只用于String类型上,不能为nulltrim()之后的size>0 @NotEmpty 用于集合类、String类不能为null,且size>0。但是带有空格的字符串校验不出来 @Size 用于对象(Array,Collection,Map,String)长度是否在给定的范围之内 @Length 用于String对象的大小必须在指定的范围内 @Pattern 用于String对象是否符合正则表达式的规则 @Email 用于String对象是否符合邮箱格式 @Min 用于NumberString对象是否大等于指定的值 @Max 用于NumberString对象是否小等于指定的值 @AssertTrue 用于Boolean对象是否为true @AssertFalse 用于Boolean对象是否为false

3.2、@Validated与@Valid区别

@Validated @Valid 是用于数据校验的注解,但它们有一些区别和应用场景的差异。

3.2.1、@Validated

  • Spring 框架提供的注解
  • 支持分组校验
  • 可以用在类型、方法和方法参数上。但是不能用在成员属性(字段)上
  • 由于无法加在成员属性(字段)上,所以无法单独完成级联校验需要配合@Valid
  • Spring 提供的校验器,默认使用的是 Hibernate Validator(实现了 JSR-303 规范),但它支持更丰富的校验场景,如分组校验。

3.2.2、@Valid

  • JDK提供的 JSR-303(Bean Validation)规范的注解
  • 不支持分组校验
  • 可以用在方法、构造函数、方法参数和成员属性(字段)上
  • 可以加在成员属性(字段)上,能够独自完成级联校验
  • 使用 @Valid 注解时,会触发 JSR-303 或者其它支持的校验框架来对被注解的对象进行校验。

3.2.3、区别

  1. 适用范围@Valid 可以应用于方法参数、返回值、字段和方法上,而 @Validated 只能应用于类、接口和方法上。
  2. 校验框架@Validated 默认使用 Hibernate Validator(实现了 JSR-303)、Spring Validator 或自定义的校验器,而 @Valid 使用的是 JSR-303 或其它支持的校验框架。
  3. 分组校验@Validated 支持分组校验,允许在不同的场景下使用不同的校验规则,而 @Valid 不直接支持分组校验。

@Validated 是 Spring 框架提供的扩展注解,并不属于 Java 标准规范。在使用时,可以根据具体的需求选择合适的注解进行数据校验。

4、使用案例

4.1、导入依赖

<!-- JSR303 -->
<hibernate.validator.version>6.0.7.Final</hibernate.validator.version><!-- JSR303 -->
<dependency><groupId>org.hibernate</groupId><artifactId>hibernate-validator</artifactId><version>${hibernate.validator.version}</version>
</dependency>

4.2、配置校验规则

在实体类里面添加配置校验

package com.tgq.model;import lombok.ToString;
import org.hibernate.validator.constraints.NotBlank;import javax.validation.constraints.NotNull;@ToString
public class MyStudent {@NotNull(message = "学生编号不能为空")private String sid;@NotBlank(message = "学生名不能为空")private String sname;@NotBlank(message = "学生年龄不能为空")private String sage;@NotBlank(message = "学生性别不能为空")private String ssex;public MyStudent(String sid, String sname, String sage, String ssex) {this.sid = sid;this.sname = sname;this.sage = sage;this.ssex = ssex;}public MyStudent() {super();}public String getSid() {return sid;}public void setSid(String sid) {this.sid = sid;}public String getSname() {return sname;}public void setSname(String sname) {this.sname = sname;}public String getSage() {return sage;}public void setSage(String sage) {this.sage = sage;}public String getSsex() {return ssex;}public void setSsex(String ssex) {this.ssex = ssex;}
}

4.3、编写校验方法

   使用@Validated注解对我们的MyStudent进行服务端校验。

    //    给数据添加服务端校验@RequestMapping("/valiAdd")public String valiAdd(@Validated MyStudent myStudent, BindingResult result, HttpServletRequest req) {
//        如果服务端验证不通过,有错误if (result.hasErrors()) {
//            服务端验证了实体类的多个属性,多个属性都没有验证通过List<FieldError> fieldErrors = result.getFieldErrors();Map<String, Object> map = new HashMap<>();for (FieldError fieldError : fieldErrors) {
//                将多个属性的验证失败信息输送到控制台System.out.println(fieldError.getField() + ":" + fieldError.getDefaultMessage());map.put(fieldError.getField(), fieldError.getDefaultMessage());}req.setAttribute("errorMap", map);} else {this.myStudentBiz.insertSelective(myStudent);return "redirect:stu/list";}return "stu/edit";}

4.4、前端代码

使用form表单进行提交

<%--Created by IntelliJ IDEA.User: tgqDate: 12/9/2023Time: 下午8:05To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head><title>edit</title>
</head>
<body><form action="${pageContext.request.contextPath }/stu/valiAdd" method="post">用户id:<input type="text" name="sid"><span style="color: red">${errorMap.sid}</span><br>用户名:<input type="text" name="sname"><span style="color: red">${errorMap.sname}</span><br>用户年龄:<input type="text" name="sage"><spanstyle="color: red">${errorMap.sage}</span><br>用户性别:<input type="text" name="ssex"><span style="color: red">${errorMap.ssex}</span><br><input type="submit" value="提交">
</form>
</body>
</html>

4.5、测试

点击提交,如果为空就会提示

二、interceptor拦截器

1、什么是拦截器?

        拦截器是在请求进入后端处理程序之前或之后执行特定逻辑的组件。它们能够拦截处理程序执行的流程,允许在请求处理过程中插入额外的功能。

        SpringMVC的处理器拦截器,类似于Servlet开发中的过滤器Filter,用于对处理器进行预处理和后处理。依赖于web框架,在实现上基于Java的反射机制,属于面向切面编程(AOP)的一种运用。由于拦截器是基于web框架的调用,因此可以使用Spring的依赖注入(DI)进行一些业务操作,同时一个拦截器实例在一个controller生命周期之内可以多次调用

2、为什么要使用拦截器?

  1. 横向功能扩展:通过拦截器,可以在不修改原有业务逻辑的情况下添加额外的功能,例如日志记录、权限验证、性能统计等。
  2. 代码复用:多个请求中可能需要相同的处理逻辑,通过拦截器可以将这部分逻辑抽取出来,减少代码的重复编写。
  3. 解耦合:通过拦截器,可以将关注点分离,在拦截器中处理通用的逻辑,使得业务处理程序更专注于业务本身。

3、拦截器与过滤器

 3.1、什么是过滤器(Filter)

依赖于servlet容器。在实现上基于函数回调,可以对几乎所有请求进行过滤,但是缺点是一个过滤器实例只能在容器初始化时调用一次。使用过滤器的目的是用来做一些过滤操作,比如:在过滤器中修改字符编码;在过滤器中修改HttpServletRequest的一些参数,包括:过滤低俗文字、危险字符等。

3.2、拦截器与过滤器的区别

3.2.1、 过滤器(filter)

  1.   filter属于Servlet技术,只要是web工程都可以使用
  2.   filter主要由于对所有请求过滤
  3.   filter的执行时机早于Interceptor

3.2.2、 拦截器(interceptor)

  1.   interceptor属于SpringMVC技术,必须要有SpringMVC环境才可以使用
  2.   interceptor通常由于对处理器Controller进行拦截
  3.   interceptor只能拦截dispatcherServlet处理的请求

3.2.3、汇总

  • 拦截器是在应用程序处理程序内部执行的,而过滤器则是在应用程序之前或之后执行的。
  • 过滤器是基于Servlet规范的,拦截器是基于应用框架的。
  • 过滤器可以在请求到达Servlet容器之前对请求进行处理,而拦截器只能在请求到达应用程序之后进行处理。

4、拦截器应用场景

  1. 权限验证:拦截器可以检查用户是否具有操作的权限,如果没有权限,可以拦截请求并返回相应的错误信息。如果没有直接返回到登录页面。
  2. 日志记录:拦截器可以记录请求的详细信息,例如请求时间、信息、请求参数等,便于后续的日志分析和故障排查。以便进行信息监控、信息统计、计算PV(Page View)等。
  3. 性能统计:拦截器可以统计请求的执行时间,便于分析系统性能并进行优化。(如果有反向代理,如apache可以自动记录);
  4. 通用行为:读取cookie得到用户信息并将用户对象放入请求,从而方便后续流程使用,还有如提取Locale、Theme信息等,只要是多个Controller中的处理方法都需要的,我们就可以使用拦截器实现。

拦截器链是由多个拦截器组成的链式结构,每个拦截器都可以在请求处理程序执行之前或之后进行特定的操作。拦截器链中的拦截器按照预定义的顺序执行,每个拦截器都有机会处理请求和响应。拦截器链可以保证各个拦截器的有序执行,以达到预期的处理逻辑。

5、使用案例

5.1、创建拦截器

创建一个拦截器的包,在包下创建拦截器

package com.tgq.interceptor;import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;public class OneInterceptor implements HandlerInterceptor {@Overridepublic boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {System.out.println("【OneInterceptor】:preHandle...");return true;//返回true / false}@Overridepublic void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {System.out.println("【OneInterceptor】:postHandle...");}@Overridepublic void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {System.out.println("【OneInterceptor】:afterCompletion...");}
}

5.2、配置拦截器

在我们的自己配置spring-mvc.xml里面配置我们的拦截器

<mvc:interceptors><bean class="com.tgq.interceptor.OneInterceptor"></bean></mvc:interceptors>

5.3、运行测试

启动项目,打开浏览器访问请求地址,测试拦截器的拦截效果。

他们的执行顺序为:preHandle --> postHandle --> afterCompletion

http://localhost:8080/sc/list

5.4、拦截器工作原理

  • preHandle:用于对拦截到的请求进行预处理,方法接收布尔(true,false)类型的返回值,返回true:放行,false:不放行。

执行时机:在处理器方法执行前执行

方法参数
参数说明
request      请求对象    
response    响应对象    
handler      拦截到的处理器方法  
ModelAndView处理器方法返回的模型和视图对象,可以在方法中修改模型和视图
  • afterCompletion:用于在整个流程完成之后进行最后的处理,如果请求流程中有异常,可以在方法中获取对象

  执行时机:视图渲染完成后(整个流程结束之后)

方法参数
参数说明
request  请求参数
response响应对象  
handler  拦截到的处理器方法
ex异常对象

5.5、拦截器链

如果多个拦截器能够对相同的请求进行拦截,则多个拦截器会形成一个拦截器链,主要理解拦截器链中各个拦截器的执行顺序。拦截器链中多个拦截器的执行顺序,根拦截器的配置顺序有关,先配置的先执行。

package com.tgq.interceptor;import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;public class TwoInterceptor implements HandlerInterceptor {@Overridepublic boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {System.out.println("【TwoInterceptor】:preHandle...");return true;}@Overridepublic void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {System.out.println("【TwoInterceptor】:postHandle...");}@Overridepublic void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {System.out.println("【TwoInterceptor】:afterCompletion...");}
}

配置spring-mvc.xml

<mvc:interceptors><!--2) 多拦截器(拦截器链)--><mvc:interceptor><mvc:mapping path="/**"/><bean class="com.tgq.interceptor.OneInterceptor"/></mvc:interceptor><mvc:interceptor><mvc:mapping path="/sc/**"/><bean class="com.tgq.interceptor.TwoInterceptor"/></mvc:interceptor></mvc:interceptors>

走一个拦截器:editicon-default.png?t=N7T8http://localhost:8080/stu/save

走两个拦截器:列表icon-default.png?t=N7T8http://localhost:8080/sc/list

5.6、登录拦截实例

5.6.1、创建拦截器

package com.tgq.interceptor;import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;public class LoginInterceptor implements HandlerInterceptor {@Overridepublic boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {System.out.println("【implements】:preHandle...");StringBuffer url = request.getRequestURL();if (url.indexOf("/login") > 0 || url.indexOf("/logout") > 0) {//        如果是 登录、退出 中的一种return true;}
//            代表不是登录,也不是退出
//            除了登录、退出,其他操作都需要判断是否 session 登录成功过String sname = (String) request.getSession().getAttribute("sname");if (sname == null || "".equals(sname)) {response.sendRedirect("/page/stu/login");return false;}return true;}@Overridepublic void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {}@Overridepublic void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {}
}

5.6.2、配置拦截器

    <!--登录拦截器实例--><mvc:interceptors><bean class="com.tgq.interceptor.LoginInterceptor"></bean></mvc:interceptors>

5.6.3、编写控制层

package com.tgq.web;import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpSession;@Controller
public class LoginController {@RequestMapping("/login")public String login(HttpServletRequest req) {String sname = req.getParameter("sname");HttpSession session = req.getSession();if ("tgq".equals(sname)) {session.setAttribute("sname", sname);}return "redirect:/sc/list";}@RequestMapping("/logout")public String logout(HttpServletRequest req) {req.getSession().invalidate();return "redirect:/sc/list";}
}

5.6.4、前端页面

<%--Created by IntelliJ IDEA.User: tgqDate: 12/9/2023Time: 下午10:03To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head><title>用户登录</title>
</head>
<body><form action="/login" method="post">账号:<input name="sname"><input type="submit">
</form>
</body>
</html>

5.6.5、测试

登入

http://localhost:8080/logouticon-default.png?t=N7T8http://localhost:8080/login

登出

http://localhost:8080/logouticon-default.png?t=N7T8http://localhost:8080/logout

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/77336.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Matlab图像处理-彩色图像基础

光谱 在17世纪60年代&#xff0c;人们普遍认为白光是一种没有其他颜色的纯色光&#xff0c;而彩色光是有某种缘故发生变化的光。为了验证这个假设&#xff0c;牛顿让一束阳光通过一面三棱镜&#xff0c;光线在墙上被分解成了八种不同的颜色&#xff0c;即&#xff1a;红、橙、…

vue基础知识九:动态给vue的data添加一个新的属性时会发生什么?怎样解决?

一、直接添加属性的问题 我们从一个例子开始 定义一个p标签&#xff0c;通过v-for指令进行遍历 然后给botton标签绑定点击事件&#xff0c;我们预期点击按钮时&#xff0c;数据新增一个属性&#xff0c;界面也 新增一行 <p v-for"(value,key) in item" :key&q…

python基于GDAL的多线程高速批量重采样、对齐栅格、对齐行列数,并无损压缩

在自己写代码处理遥感数据进行波段计算&#xff0c;或者基于遥感等空间数据进行机器学习、深度学习时&#xff0c;一般都需要各图层行列数一致。在QGIS中有“对齐栅格”工具可以完成该任务&#xff0c;但是QGIS中没有提供批量操作的接口&#xff0c;在数据比较多时&#xff0c;…

eslint写jsx报错

eslint写jsx报错 ChatGPT提示 在写JSX时&#xff0c;ESLint可能会报出一些语法错误&#xff0c;这些错误通常是由于ESLint默认配置中不支持JSX语法导致的。为了解决这些错误&#xff0c;我们需要在ESLint配置文件中启用对JSX语法的支持。 首先&#xff0c;需要安装eslint-pl…

时序分解 | MATLAB实现基于EWT经验小波变换的信号分解分量可视化

时序分解 | MATLAB实现基于EWT经验小波变换的信号分解分量可视化 目录 时序分解 | MATLAB实现基于EWT经验小波变换的信号分解分量可视化效果一览基本介绍程序设计参考资料 效果一览 基本介绍 EWT经验小波变换 包含频谱相关系数 可直接运行 Matlab代码 1.可自由设置分量个数&…

SpringBoot整合Easy-ES操作演示文档

文章目录 SpringBoot整合Easy-ES操作演示文档1 概述及特性1.1 官网1.2 主要特性 2 整合配置2.1 导入POM2.2 Yaml配置2.3 EsMapperScan 注解扫描2.4 配置Entity2.5 配置Mapper 3 基础操作3.1 批量保存3.2 数据更新3.3 数据删除3.4 组合查询3.5 高亮查询3.6 统计查询 4 整合异常4…

prize_p1

文章目录 解题过程代码审计思路问题解决数组绕过preg_match__destruct的触发修改phar文件以及签名phar://支持的后缀 题解方法一&#xff08;数组绕过&#xff09;方法二&#xff08;gzip绕过&#xff09; 解题过程 源代码 <META http-equiv"Content-Type" conte…

AI文本创作在百度App发文的实践

作者 | 内容生态端团队 导读 大语言模型&#xff08;LLM&#xff09;指包含数百亿&#xff08;或更多&#xff09;参数的语言模型&#xff0c;这些模型通常在大规模数据集上进行训练&#xff0c;以提高其性能和泛化能力。在内容创作工具接入文心一言AI能力后&#xff0c;可以为…

论文复现--lightweight-human-pose-estimation-3d-demo.pytorch(单视角多人3D实时动作捕捉DEMO)

分类&#xff1a;动作捕捉 github地址&#xff1a;https://github.com/Daniil-Osokin/lightweight-human-pose-estimation-3d-demo.pytorch 所需环境&#xff1a; Windows10&#xff0c;conda 4.13.0&#xff1b; 目录 conda环境配置安装Pytorch全家桶安装TensorRT&#xff08;…

C++设计模式_05_Observer 观察者模式

接上篇&#xff0c;本篇将会介绍C设计模式中的Observer 观察者模式&#xff0c;和前2篇模板方法Template Method及Strategy 策略模式一样&#xff0c;仍属于“组件协作”模式。Observer 在某些领域也叫做 Event 。 文章目录 1. 动机&#xff08; Motivation&#xff09;2. 代码…

红帽 RHEL 源码限制成契机,AlmaLinux 获捐更可“做自己”

红帽在两个月前发布公告声称&#xff0c;将限制对 Red Hat Enterprise Linux (RHEL) 源代码的访问&#xff0c;早前曾报道&#xff0c;此举导致 AlmaLinux 、Rocky Linux 等 Linux 发行版未来发展严重受阻。 对于这一决策&#xff0c;AlmaLinux OS 基金会主席 Benny Vasquez 此…

few shot目标检测survey paper笔记(整体概念)

paper: Few-Shot Object Detection: A Comprehensive Survey (CVPR2021) 深度学习提高了目标检测的精度&#xff0c;但是它需要大量的训练数据。 对于训练数据集中没有见过的目标&#xff0c;是检测不了的&#xff0c;所以就限制了在实际中的应用。 如果想让模型去识别新的目标…

element-table 行的拖拽更改顺序(无需下载sortableJs

样例展示&#xff1a;vueelement 通过阅读element文档我们发现element并不提供拖拽相关的api 本博客通过element提供的行类名 注册函数 实现行与行的拖拽 1.设置el-table 的行样式类名 这里是用的是 function <el-table:data"outputData":row-class-name&qu…

H.265 视频在浏览器中的播放问题探究

&#x1f337;&#x1f341; 博主猫头虎&#xff08;&#x1f405;&#x1f43e;&#xff09;带您 Go to New World✨&#x1f341; &#x1f405;&#x1f43e;猫头虎建议程序员必备技术栈一览表&#x1f4d6;&#xff1a; &#x1f6e0;️ 全栈技术 Full Stack: &#x1f4da…

2023/9/12 -- C++/QT

作业 实现一个图形类&#xff08;Shape&#xff09;&#xff0c;包含受保护成员属性&#xff1a;周长、面积&#xff0c; 公共成员函数&#xff1a;特殊成员函数书写 定义一个圆形类&#xff08;Circle&#xff09;&#xff0c;继承自图形类&#xff0c;包含私有属性&#xf…

X86_64函数调用汇编程序分(2)

X86_64函数调用汇编程序分&#xff08;2&#xff09; 1 X86_64寄存器使用标准2 leaveq和retq指令2.1 leaveq2.2 retq 3 执行leaveq和retq之后栈的结构3.1 执行leaveq之后栈的结构3.1.1 test_fun_b函数执行leaveq之前的栈结构示意图3.1.2 test_fun_b函数执行leaveq之后的栈结构示…

Charles的Map Remote功能

1、charles的Map Remote功能&#xff08;指定的网络请求重定向到另一个网址&#xff09;&#xff0c;说白了就是你本来要请求A接口拿数据&#xff0c;重定向后&#xff0c;你实际请求的是B接口&#xff0c;拿到的是B接口返回的数据。 入口Tools->Map Remote 本次测试过程中…

第三节:在WORD为应用主窗口下关闭EXCEL的操作(2)

【分享成果&#xff0c;随喜正能量】凡事好坏&#xff0c;多半自作自受&#xff0c;既不是神为我们安排&#xff0c;也不是天意偏私袒护。业力之前&#xff0c;机会均等&#xff0c;毫无特殊例外&#xff1b;好坏与否&#xff0c;端看自己是否能应机把握&#xff0c;随缘得度。…

Trinitycore学习之在vscode查看远端服务器上源码配置

1&#xff1a;安装vscode&#xff0c;去官网下载&#xff0c;这里下载windows版本安装包 .zip https://code.visualstudio.com/Download 2&#xff1a;安装后&#xff0c;安装扩展chinese&#xff0c;使用中文设置&#xff0c;需要重启vscode。 3&#xff1a;安装ssh相关插件…

Springmvc之JSR303和拦截器

JSR303拦截器 1.JSR303 什么是JSR303 JSR是Java Specification Requests的缩写&#xff0c;意思是Java 规范提案。是指向JCP(Java Community Process)提出新增一个标准化技术规范的正式请求。任何人都可以提交JSR&#xff0c;以向Java平台增添新的API和服务。JSR已成为Java界的…