Java-38 深入浅出 Spring - AOP切面增强 核心概念 相关术语 Proxy配置

news2025/1/5 8:33:37

点一下关注吧!!!非常感谢!!持续更新!!!

大数据篇正在更新!https://blog.csdn.net/w776341482/category_12713819.html

在这里插入图片描述

目前已经更新到了:

  • MyBatis(已更完)
  • Spring(正在更新…)

在这里插入图片描述

章节内容

上节我们完成了:

  • 循环依赖 原型Bean
  • 原型作用域 Lazy
  • ObjectFactory

Spring AOP

AOP 的本质:在不改变原有逻辑的情况下,增强横切的逻辑,横切逻辑代码往往是权限校验代码、日志代码、事务控制代码、性能监控代码。

Spring AOP(面向切面编程,Aspect-Oriented Programming)是Spring框架的一部分,提供了基于代理的AOP功能。它允许你在不改变原有代码的情况下,向应用程序中添加额外的功能或行为。Spring AOP通过切面(Aspect)、连接点(Joinpoint)、通知(Advice)和切点(Pointcut)等概念提供了对程序流的控制,帮助实现横切关注点的模块化。横切关注点指的是跨越多个类或模块的功能,比如日志记录、事务管理、安全控制等。

核心概念

切面(Aspect)

切面是AOP的核心概念,表示横切关注点的模块化。切面是由切点和通知组成的,切面定义了哪些方法会应用额外的功能(通知)。

连接点(Joinpoint)

连接点表示程序执行中的一个点,比如方法调用、方法执行、构造函数调用等。Spring AOP中的连接点通常是方法执行的地方。

切点(Pointcut)

切点定义了哪些连接点是需要拦截的,它通常是基于方法签名进行筛选的。例如,选择某个包下所有的方法,或者某个类的方法。切点是一个表达式,表示何时需要执行通知。

通知(Advice)

通知定义了在连接点上执行的代码,通知决定了增强的具体行为。通知有不同的类型,分别是:

  • 前置通知(Before):方法执行前执行。
  • 后置通知(After):方法执行后执行,不论方法是否抛出异常。
  • 返回通知(AfterReturning):方法正常执行完后执行。
  • 异常通知(AfterThrowing):方法抛出异常时执行。
  • 环绕通知(Around):可以控制方法的执行,既可以选择执行方法,也可以选择不执行方法,或者修改方法的返回值。
  • 目标对象(Target Object):

目标对象是被AOP代理的对象,它是切面操作的实际对象。

Spring AOP的工作原理

Spring AOP基于代理模式来实现,它主要通过两种方式生成代理对象:

  • JDK动态代理:适用于目标对象实现了接口的情况。Spring会生成目标对象接口的代理类。
  • CGLIB代理:适用于目标对象没有实现接口的情况。Spring会通过CGLIB库生成目标对象的子类作为代理。

Spring AOP的优缺点

优点

  • 解耦:Spring AOP允许将横切关注点从核心业务逻辑中分离出来,增强了模块化。
  • 透明性:通过AOP,开发人员可以不改变原有代码,增加新的功能。
  • 灵活性:通过切面、通知、切点的灵活配置,可以精确控制横切功能的执行。

缺点

  • 性能开销:因为每个代理对象都会拦截方法调用,可能会对性能产生影响,特别是在复杂的应用中。
  • 复杂性:对于初学者来说,理解AOP的概念和Spring AOP的配置可能有一定的难度。

相关术语

业务主线

在讲解 AOP 术语之前,我们先来看一下这些图,它们的第三部分案例需求的扩展(针对这些扩展的需求,我们只进行分析,在这个基础上进一步去回顾 AOP)

在这里插入图片描述
上图描述的就是未采用的 AOP 思想的设计的程序,当我们红色框中圈定的方法时,会带来大量的重复劳动,程序中充斥着大量的重复代码,使我们程序的独立性很差,而下图中采用了 AOP 思想涉及的程序,它把红框部门的代码抽取出来的同时,运用动态代理技术,在运行期间对需要使用业务逻辑方法进行增强。

在这里插入图片描述

AOP术语

  • JoinPoint 连接点:它指的是那些可以用于增强代码加入到业务主线中的点,那么由上图中我们可以看出,这些点指的就是方法。在方法执行的前后通过动态代理的技术加入增强的代码。在 Spring 的框架 AOP思想的技术实现中,也只支持方法类型的连接点。
  • Pointcut 切点:它指的是已经增强的代码加入业务主线进行之后的连接点,由上图中,我们看出表现层 transfer 方法就只是连接点,因为判断访问权限的功能并没有对其进行增强。
  • Advice 通知增强:它指的是切面中用于提供增强功能的方法,并且不同方法增强的时机是不一样的。比如,开启事务肯定是在要在业务方法执行之前的,提交事务要肯定在业务方法执行之后的,而回滚的执行需要在业务方法出现错误的时候再执行。这些就是通知类型,目前的分类有:前置通知、后置通知、异常通知、最终通知、环绕通知。
  • Target 目标对象:它指的是代理的目标对象,即被代理对象
  • Proxy 代理对象:它指的是一个类被 AOP 织入增强后,产生的代理类,即代理对象。
  • Weaving 织入:它指的是增强应用到目标对象来创建新的代理的过程,Spring 采用动态代理织入,而 AspectJ 采用编译期间织入和类装载期间织入。
  • Aspect 切面:它指定是增强的代码所关注的方面,把这些相关的增强代码定义到一个类中,这个类就是切面,例如,事务切面,它里面定义的方法和事务相关的,像开启事务、提交事务、回滚事务等等,不会定义其他与事务无关的方法,之前提到的TransactionManager 就是一个切面。

这里还需要进行一定的解释:

  • 连接点:方法开始时、结束时、正常运行完毕的时候、方法异常的时候等等,这些特殊的时间点,我们称做连接点,项目中每个方法都有连接点,连接点是一种候选点。
  • 切入点:指定 AOP 思想要影响的具体的方法是哪些
  • Advice 增强,第一个层次:指的是横切逻辑
  • Adevice 增强,第二个层次:方位点(在某一些连接点上加入横切逻辑,那么这些连接点就叫做方位点,描述的是具体的特殊时机)
  • Aspect:切面概念是对上述概念的一个综合解释,切面=切入点+增强

AOP 代理选择

Spring 实现 AOP 思想使用的动态代理技术,默认情况下,Spring 会根据被代理对象是否实现接口来选择JDK 还是 CGLIB,当被代理对象实现了接口,Spring 会选择 JDK 官方的代理技术,不过我们可以通过配置的方式,让 Spring 强制使用 CGLIB 的方式。

AOP 配置方式

在 Spring 的 AOP 的配置中,和 IoC 配置一样,支持三类的配置方式:

  • 使用 XML 配置
  • 使用 XML + 注解的方式配置
  • 使用纯注解的方式配置

AOP 实现

需求描述

横切逻辑代码是打印日志,希望打印日志的逻辑织入到目标方法的特定位置

添加依赖

我们需要在 pom 中添加依赖:

<dependency>
 <groupId>org.springframework</groupId>
 <artifactId>spring-aop</artifactId>
 <version>5.1.12.RELEASE</version>
</dependency>
<dependency>
 <groupId>org.aspectj</groupId>
 <artifactId>aspectjweaver</artifactId>
 <version>1.9.4</version>
</dependency>

核心配置

我们在基于 XML 的配置步骤如下:

  • 把通知的 Bean 交给 Spring 管理
  • 使用 aop:config 开始 AOP 的配置
  • 使用 aop:aspect 配置切面
  • 使用对应的标签配置通知的类型,入门的案例采用前置通知,标签为 aop:before
<!-- 日志工具 交由给 Spring 进行管理 -->
<bean id="wzkLogUtils" class="wzk.utils.WzkLogUtils"></bean>
<!-- AOP 配置 -->
<aop:config>
    <!-- 配置切面 -->
    <aop:aspect id="wzkLogAdvice" ref="wzkLogUtils">
        <aop:before method="printLog" pointcut="execution(public * wzk.service.impl.WzkTransferServiceImpl.update(wzk.model.WzkAccount))"></aop:before>
    </aop:aspect>
</aop:config>

对应的代码如下所示:
在这里插入图片描述
上述的配置实现了 WzkTransferServiceImpl.update 方法进行了增强,在其执行之前,输出了记录日志的语句,这里有一个新的概念:【切入点表达式】

切入点表达式

切入点表达式也叫做 AspectJ 切入点表达式,指的是遵循特定的语法结构的字符串,其作用的是用于对符合的语法格式的连接点进行增强,它是 AspectJ 的一部分。
AspectJ 是一个基于 Java 的 AOP 框架,Spring 框架从 2.0 版本之后集成了 AspectJ 框架中切入点表达式部分,开始支持 AspectJ 切入点表达式。

改变代理的配置

改变代理的配置,Spring 在选择创建代理的时候,会根据被代理对象实际情况来选择的,被代理对象实现了接口,则采用基于接口的动态代理,当被代理对象没有实现任何接口的时候,Spring 会自动切换到基于子类的动态代理方式。
但是我们都知道,无论被代理对象是否实现接口,只要不是 final 修饰的类都可以采用 CGLIB 提供的方式创建代理对象,所以 Spring 也考虑到了这个情况,提供了配置方式实现强制使用基于子类的动态代理(即 CGLIB 的方式),配置的方式有两种:

  • aop:config 标签来配置 proxy-target-class=“true”
  • aop:aspectj-autoproxy 标签来配置 proxy-target-class=“true”

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

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

相关文章

基于Docker+模拟器的Appium自动化测试(二)

模拟器的设置 打开“夜神模拟器”的系统设置&#xff0c;切换到“手机与网络”页&#xff0c;选中网络设置下的“开启网络连接”和“开启网络桥接模式”复选框&#xff0c;而后选择“静态IP”单选框&#xff0c;在IP地址中输入“192.168.0.105”&#xff0c;网关等内容不再赘述…

【从零开始入门unity游戏开发之——C#篇36】C#的out协变和in逆变如何解决泛型委托的类型转换问题

文章目录 一、知识回顾和问题分析1、回顾强制转换和as转换知识2、问题分析 二、为什么泛型委托不行&#xff1f;1、泛型类型的严格类型检查2、**as 和强制类型转换不能直接使用** 三、如何解决这个问题&#xff1f;1、**协变&#xff08;out&#xff09;**2、**逆变&#xff08…

深度学习使用Anaconda打开Jupyter Notebook编码

新手入门深度学习使用Anaconda打开Jupyter Notebook编码 1. 安装Anaconda 第一种是Anaconda官网下载安装包&#xff0c;但是很慢&#xff0c;不太建议 第二种使用国内清华大学镜像源下载 选择适合自己电脑的版本&#xff0c;支持windows&#xff0c;linux系统 下载完之后自行…

Linux套接字通信学习

Linux套接字通信 代码源码&#xff1a;https://github.com/say-Hai/TcpSocketLearn/tree/CThreadSocket 在网络通信的时候, 程序猿需要负责的应用层数据的处理(最上层)&#xff0c;而底层的数据封装与解封装&#xff08;如TCP/IP协议栈的功能&#xff09;通常由操作系统、网络协…

git clone 和 conda 换源

文章目录 git clone 通过 sshconda 创建虚拟环境通过 env.yml 文件conda 换源 git clone 通过 ssh git clone ssh://用户名IP地址:/仓库名字.gitconda 创建虚拟环境通过 env.yml 文件 conda env create -f environment.ymlconda 换源 Step 1 生成 .bashrc 文件在家目录下。…

机床数据采集网关在某机械制造企业的应用

随着工业4.0时代的到来&#xff0c;智能制造已成为制造业转型升级的重要方向。数控机床作为现代制造业的核心设备&#xff0c;其运行状态和加工参数的数据实时采集与分析对于提升生产效率、优化生产流程具有关键意义。 背景概述 某机械制造企业拥有多台数控机床&#xff0c;这…

c# RSA加解密工具,.netRSA加解密工具

软件介绍 名称: c# RSA加解密工具,.netRSA加解密工具依赖.net版本: .net 8.0工具类型: WinForm源码下载 c# RSA加解密工具,.netRSA加解密工具 依赖项 WinFormsRSA.csproj <Project

穷举vs暴搜vs深搜vs回溯vs剪枝_全排列_子集

46. 全排列 递归解决&#xff1a;一开始选一个数&#xff0c;递归进入下一层再选一个新的数&#xff0c;直到到最后一个数。反会上一层遍历其它数。 每次递归到叶子节点就找到了一种组合&#xff0c;思路有了具体怎么实现&#xff1f; 1.怎么记录每条路径&#xff1f; 定义一个…

【Trick】获取kaggle账号的token和api(用于数据集下载)

0&#xff1a;操作背景 由于未来的科研需要用到Unet&#xff0c;但是运行学长的史山代码无法跑通&#xff0c;自己写了一个Unet并load学长的数据集效果也很差&#xff0c;于是打算从最最基础的开始&#xff0c;上github调用一个Unet并成功在公有数据集上跑一遍实例。 Unet的g…

VS Code AI开发之Copilot配置和使用详解

随着AI开发工具的迅速发展&#xff0c;GitHub Copilot在Cursor、Winsuf、V0等一众工具的冲击下&#xff0c;推出了免费版本。接下来&#xff0c;我将为大家介绍GitHub Copilot的配置和使用方法。GitHub Copilot基于OpenAI Codex模型&#xff0c;旨在为软件开发者提供智能化的代…

论文解读 | NeurIPS'24 Lambda:学习匹配先验以处理无标记垂悬问题场景下的实体对齐任务...

点击蓝字 关注我们 AI TIME欢迎每一位AI爱好者的加入&#xff01; 点击 阅读原文 观看作者讲解回放&#xff01; 作者简介 尹航&#xff0c;上海交通大学博士生 内容简介 我们研究了带有无标记悬挂问题的实体对齐&#xff08;EA&#xff09;任务&#xff0c;即部分实体在另一个…

评分模型在路网通勤习惯分析中的应用——提出问题(1)

1、问题的由来、目标和意义 最近一段时间和公司其它业务部门讨论时&#xff0c;发现一个有趣的交通路网问题&#xff0c;车辆从S点行驶到V点共用时40分钟&#xff0c;这段时间内路网中的卡口摄像头识别到了车辆通过的信息。如下图所示&#xff1a; 设计师需要通过这些有限的路…

Spring Security day 11.23

ok了今天学习一个关于登录角色权限的管理框架&#xff0c;我们一起取看看吧 一.权限控制 1.1 认证和授权概念 前面我们已经完成了后台管理系统的部分功能&#xff0c;例如检查项管 理、检查组管理、套餐管理、预约设置等。接下来我们需要思 考 2 个问题&#xff1a; 问题 1 …

【IC验证】verilog及systemverilog特殊特性的分析

verilog及systemverilog特殊特性的分析 1.概述2.赋值延迟&#xff08;0&#xff09;总结&#xff08;1&#xff09;情况一&#xff1a;initial中进行阻塞赋值和非阻塞赋值&#xff08;不延迟&#xff09;a代码b 电路图c 结果 &#xff08;2&#xff09;时钟a 代码b 电路图c 结果…

FPGA流水线考虑因素

流水线考虑因素 另一种提升性能的方法是对拥有多个逻辑级数的长数据路径进行重新组织&#xff0c;并将其分配在多个时钟周期上。这种方法 以时延和流水线开销逻辑管理为代价&#xff0c;来达到加快时钟周期和提高数据吞吐量的目的。 由于 FPGA 器件带有大量的寄存器&#x…

关于 PCB线路板细节锣槽问题 的解决方法

若该文为原创文章&#xff0c;转载请注明原文出处 本文章博客地址&#xff1a;https://hpzwl.blog.csdn.net/article/details/144783817 长沙红胖子Qt&#xff08;长沙创微智科&#xff09;博文大全&#xff1a;开发技术集合&#xff08;包含Qt实用技术、树莓派、三维、OpenCV…

SQL创建和操纵表

本文介绍创建、更改和删除表的基本知识。 1. 创建表 SQL 不仅用于表数据操纵&#xff0c;而且还用来执行数据库和表的所有操作&#xff0c;包括表本身的创建和处理。一般有两种创建表的方法&#xff1a; 多数DBMS 都具有交互式创建和管理数据库表的工具&#xff1b;表也可以…

RPA系列-uipath 学习笔记4

使用Uipath 处理hover的问题 备注&#xff1a;使用uipath stversion&#xff1a;2024.10.6,所有学习来源自uipath Academy 首先&#xff0c;打开uipath给我们提供的一个网站 ACME,这个网站呢&#xff0c;需要提前注册一下的哈。 今天呢&#xff0c;就是记录一下&#xff0c;怎…

Unity编译Android apk包进度奇慢或gradle报错的解决方案

最近遇到Unity编译Android apk进度卡在"Calling IPostGenerateGradleAndroidProject callbacks"进度一直不变&#xff0c;如下图&#xff1a; 最后提示编译失败&#xff0c;类似错误如下&#xff1a; Picked up JAVA_TOOL_OPTIONS: -Dfile.encodingUTF-8FAILURE: Bu…

探究音频丢字位置和丢字时间对pesq分数的影响

丢字的本质 丢字的本质是在一段音频中一小段数据变为0 丢字对主观感受的影响 1. 丢字位置 丢字的位置对感知效果有很大影响。如果丢字发生在音频信号的静音部分或低能量部分&#xff0c;感知可能不明显&#xff1b;而如果丢字发生在高能量部分或关键音素上&#xff0c;感知…