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

【Spring】aop的底层原理

🎄欢迎来到@边境矢梦°的csdn博文🎄

 🎄本文主要梳理 Spring 中的切面编程aop的底层原理和重点注意的地方 🎄
🌈我是边境矢梦°,一个正在为秋招和算法竞赛做准备的学生🌈
🎆喜欢的朋友可以关注一下🫰🫰🫰,下次更新不迷路🎆

Ps: 月亮越亮说明知识点越重要 (重要性或者难度越大)🌑🌒🌓🌔🌕  

 

目录

❤️切面编程介绍

🌸连接点和切入点的区别🚀

🌈Spring中扫描包注册bean

✨Spring中切面编程的两种实现

🎈切入表达式


❤️切面编程介绍

🎈Spring的切面编程是通过AOP(面向切面编程)机制来实现。AOP是一种编程范式,旨在将横切关注点(如日志记录、事务管理等)与核心业务逻辑分离以提高代码的模块性、可重用性和可维护性。

在Spring中,切面由两部分组成:切点(Pointcut)和通知(Advice)。

📌切点定义了在哪些连接点上应用切面逻辑。连接点是程序执行过程中可以插入切面逻辑的特定点,例如方法的执行、方法的调用等。切点可以使用表达式来选择特定的连接点,可以根据方法名、类名、注解等条件进行选择。

📌通知是切面逻辑的具体实现。它定义了在切点上要执行的行为,可以在切点的前后、异常抛出时、方法返回时等时机执行。常见的通知类型包括前置通知(Before)、后置通知(After)、异常通知(AfterThrowing)和返回通知(AfterReturning)等。

✍️除了切点和通知,切面还可以包括引入(Introduction)和切面顺序(Aspect Ordering)等功能。引入允许在现有类中添加新的方法和属性以增强类的功能。切面顺序定义了多个切面的执行顺序,以控制切面逻辑的执行顺序。

在Spring中,切面可以通过XML配置基于注解的配置或者基于Java的配置来定义。Spring提供了多种AOP实现,✨包括基于JDK的动态代理和基于CGlib的字节码生成。

🎉通过使用Spring的切面编程,可以将共同的横切关注点从核心业务逻辑中剥离出来,以提高代码的可维护性和可重用性。切面编程在日志记录、事务管理、安全性控制等方面有广泛的应用。


🌸连接点和切入点的区别🚀

在Spring框架的AOP编程中,连接点(Join Point)和切入点(Pointcut)是两个相关但不同的概念。

📌连接点是在程序执行过程中,可以插入切面逻辑的特定点。这些点可以是方法的执行、方法的调用或者异常的抛出等。在Spring中,连接点通常是方法的执行。连接是bean中的一些点

📌切入点是指在连接点中选择特定的连接点。它是一个表达式,描述了哪些连接点将被切面逻辑所应用。切入点可以根据方法名、类名、注解等条件来选择特定的连接点。

换句话说,切入点是一个定义,它决定了在哪些连接点上切面逻辑将会被执行。连接点是实际的程序执行点(Bean的),而切入点是定义了在哪些连接点上应用切面逻辑的规则。

🌰例如,可以通过切入点表达式来选择在所有的Service接口的方法执行时应用切面逻辑。而连接点则是具体的某个Service接口的方法执行。

在Spring AOP中,切入点表达式是使用AspectJ切入点表达式语言编写的,它具有灵活的语法,可以根据需求选择不同的连接点。(下文中)


🌈Spring中扫描包注册bean

🥝切面类不需要扫描进bean

在Spring中,当你使用 <context:component-scan> 进行包扫描时,它默认会扫描指定包及其子包中的类,并将带有特定注解的类注册为Spring容器中的bean。如果类没有加上注解,它将不会被注册为bean,也就不会被Spring进行管理。

然而,与AOP(面向切面编程)有关的切面通常不需要被注册为bean,因为它们是通过特定的AOP配置来创建和管理的。切面通常是带有 @Aspect 注解的类,并且它们的方法可以使用 @Before@After 等注解来定义切面逻辑。

所以,如果你的切面类(带有 @Aspect 注解的类)在指定的包中,它会被扫描到,但不会被注册为Spring容器中的bean。相反,Spring会使用AOP配置来创建并管理这些切面,例如使用 <aop:aspectj-autoproxy>@EnableAspectJAutoProxy 这样的配置来启用自动代理,从而将切面应用到相应的bean中。

总之,不需要将切面类注册为Spring bean,Spring会自动处理AOP相关的配置和代理生成。只需确保切面类在扫描的包中以及AOP配置正确即可。

🥝切面应用到的目标bean需要被扫描进bean

切面应用到的目标bean通常需要被Spring加载进容器中,以便Spring可以管理这些bean并应用切面的横切关注点(cross-cutting concerns)。

🏀总结切面的流程

具体来说,当你使用Spring AOP来应用切面时,以下是通常的流程:

  1. 你定义了一个切面类,该类使用 @Aspect 注解进行标记,同时定义了切面逻辑,如@Before、@After等通知。

  2. 你还定义了一个或多个目标bean,这些bean是你的应用程序的组成部分,切面将会应用到这些bean的方法上。

  3. Spring容器会扫描并加载这些目标bean,将它们实例化并管理它们的生命周期。

  4. 你配置Spring AOP,告诉Spring在哪些切点(方法执行点)应用你的切面。这通常通过<aop:aspectj-autoproxy>@EnableAspectJAutoProxy 这样的配置来完成。

  5. Spring会自动为目标bean创建代理对象,这些代理对象包含了切面逻辑。当你调用目标bean的方法时,切面逻辑会在方法执行前后生效,从而实现横切关注点的功能。

所以,虽然切面类本身不需要被显式注册为Spring bean,但目标bean需要被Spring加载并纳入容器管理,以便切面可以应用到它们的方法上。这就是Spring AOP的工作原理。


✨Spring中切面编程的两种实现

在Spring AOP中,不仅可以对实现了接口的bean进行切面编程,还可以对没有实现接口的bean进行切面编程。Spring使用代理对象来实现AOP,而代理对象可以基于接口(JDK动态代理)基于类(CGLIB代理)创建因此不需要目标bean实现接口也可以应用切面。

具体取决于AOP代理的方式:

  1. JDK动态代理:当目标bean实现了接口时,Spring会使用JDK动态代理来创建代理对象。这意味着只有实现了接口的方法才能被切面所影响。

  2. CGLIB代理:当目标bean没有实现接口时,Spring会使用CGLIB代理来创建代理对象。CGLIB可以代理没有实现接口的类,因此可以应用到这些类的方法。

✍️两个动态代理的区别

  1. JDK动态代理是面向接口的,只能增强实现类中接口中存在的方法。CGlib是面向父类的,可以增强父类的所有方法
  2. JDK得到的对象是JDK代理对象实例,而CGlib得到的对象是被代理对象的子类

📌要注意的是,如果你使用基于注解的切面编程(例如使用 @Aspect 注解),Spring AOP会自动选择适当的代理方式,无需手动指定只需确保你的切面和目标bean都配置正确,Spring会处理代理的创建和切面的应用。

所以,Spring AOP可以用于实现对实现接口和未实现接口的bean的切面编程。选择代理方式取决于目标bean是否实现了接口。

🎈切入表达式

📌图来自 : (III)AOP:第四节:切入点表达式 - 格物致知_Tony - 博客园 (cnblogs.com)

 切入点表达式

🥝作用
通过表达式的方式定位一个或多个具体的连接点。
🌸🌈语法细节
①切入点表达式的语法格式

execution([权限修饰符][返回值类型][简单类名/全类名][方法名]([参数列表]))

②🌰 基本使用

表达式execution(* com.sina.spring.ArithmeticCalculator.*(..))
含义

ArithmeticCalculator接口中声明的所有方法。

第一个“*”代表任意修饰符及任意返回值。

第二个“*”代表任意方法。
“..”匹配任意数量、任意类型的参数。
若目标类、接口与该切面类在同一个包中可以省略包名。

表达式execution(public * ArithmeticCalculator.*(..))
含义ArithmeticCalculator接口的所有公有方法
表达式execution(public double ArithmeticCalculator.*(..))
含义ArithmeticCalculator接口中返回double类型数值的方法
表达式execution(public double ArithmeticCalculator.*(double,..))
含义

第一个参数为double类型的方法。

“..”匹配任意数量、任意类型的参数。

表达式execution(public double ArithmeticCalculator.*(double, double))
含义参数类型为double,double类型的方法
表达式execution(* *.add(int,….)) l execution(* *.sub(int,..))
含义任意类中第一个参数为int类型的add方法或sub方法

相关文章:

【Spring】aop的底层原理

&#x1f384;欢迎来到边境矢梦的csdn博文&#x1f384; &#x1f384;本文主要梳理 Spring 中的切面编程aop的底层原理和重点注意的地方 &#x1f384; &#x1f308;我是边境矢梦&#xff0c;一个正在为秋招和算法竞赛做准备的学生&#x1f308; &#x1f386;喜欢的朋友可以…...

微信小程序开发---基本组件的使用

目录 一、scroll-view &#xff08;1&#xff09;作用 &#xff08;2&#xff09;用法 二、swiper和swiper-item &#xff08;1&#xff09;作用 &#xff08;2&#xff09;用法 三、text &#xff08;1&#xff09;作用 &#xff08;2&#xff09;使用 四、rich-tex…...

SpringBoot国际化配置组件支持本地配置和数据库配置

文章目录 0. 前言i18n-spring-boot-starter1. 使用方式0.引入依赖1.配置项2.初始化国际化配置表3.如何使用 2. 核心源码实现一个拦截器I18nInterceptorI18nMessageResource 加载国际化配置 3.源码地址 0. 前言 写个了原生的SpringBoot国际化配置组件支持本地配置和数据库配置 背…...

Shell编程之sort

sort 命令将文件的每一行作为比较对象&#xff0c;通过将不同行进行相互比较&#xff0c;从而得到最终结果。从首字符开始&#xff0c;依次按ASCII码值进行比较&#xff0c;最后将结果按升序输出。 基本语法 sort (选项)(参数) 常用选项 常用选项 -n根据字符串的数字比较-r…...

windows docker 容器启动报错:Ports are not available

docker 启动容器报错&#xff1a; (HTTP code 500) server error - Ports are not available: listen tcp 0.0.0.0:6379: bind: An attempt was made to access a socket in a way forbidden by its access permissions. 问题排查 检查端口是否被其它程序占用&#xff1a;nets…...

300. 最长递增子序列

题目描述 给你一个整数数组 nums &#xff0c;找到其中最长严格递增子序列的长度。 子序列 是由数组派生而来的序列&#xff0c;删除&#xff08;或不删除&#xff09;数组中的元素而不改变其余元素的顺序。例如&#xff0c;[3,6,2,7] 是数组 [0,3,1,6,2,2,7] 的子序列。 示…...

DNS(域名解析系统)

含义 当我们在上网要访问莫个服务器的时候&#xff0c;就需要知道服务器的IP地址&#xff0c;但IP地址是一串数字&#xff0c;虽然这串数字用点分十进制已经清晰不少了&#xff0c;但还是不利于人们记忆和传播&#xff0c;于是人们使用单词来代替IP地址&#xff08;例如baidu&a…...

解决jsp/html界面跳转servlet出现404错误的方法

解决jsp/html界面跳转servlet出现404错误的方法 最近在学习黑马项目过程中遇到的问题 问题一&#xff1a; 检查页面的跳转路径和名称拼写是否正确 问题二&#xff1a; tomcat发布项目时所使用的路径名称与项目不同 在idea右上角点击如图圈住的按钮 在deployment中更改出现…...

catface,使用Interface定义Controller,实现基于Http协议的RPC调用

catface 前言cat-client 模块EnableCatClientCatClientCatMethodCatNoteCatResponesWrapperCatClientConfigurationCatClientProviderCatClientFactoryCatSendInterceptorCatHttpCatPayloadResolverCatObjectResolverCatLoggerProcessorCatResultProcessorCatSendProcessorAbst…...

Linux:LVS (NAT群集搭建)

模拟环境 外网入口服务器 外网 192.168.8.88 内网ip 192.168.254.4 web1 服务器 ip 192.168.254.1 网关&#xff1a; 192.168.254.4 web2 服务器 ip 192.168.254.2 网关&#xff1a; 192.168.254.4 共享存储服务器 ip 192.168.254.3 介绍 访问 外网192.16…...

音乐格式转换mp3怎么转?跟着步骤操作一遍

音乐格式转换mp3怎么转&#xff1f;mp3&#xff0c;一种音频数据压缩格式&#xff0c;由于其极具优势的文件尺寸小和高质量音效&#xff0c;自诞生之日起就占据了主流音乐格式的头把交椅&#xff0c;并且至今仍然受到用户的青睐&#xff0c;稳居音乐领域的霸主地位。在我们繁忙…...

it监控系统可以电脑吗?有什么效果

IT业务监控已经成为公司不可或缺的一部分&#xff0c;以确保业务的正常运行&#xff0c;提高企业的竞争能力。本文将详细介绍IT业务监控的必要性、实施方法以及如何选择合适的监控工具。 IT业务监控的必要性 确保业务稳定运行  IT业务监控可以实时检测公司的工作流程&#x…...

jvs-智能bi(自助式数据分析)9.1更新内容

​jvs-智能bi更新功能 1.报表增加权限功能&#xff08;服务、模板、数据集、数据源可进行后台权限分配&#xff09; 每个报表可以独立设置权限&#xff0c;通过自定义分配&#xff0c;给不同的人员分配不同的权限。 2.报表新增执行模式 可选择首次报表加载数据为最新数据和历…...

MyBatis-Plus-扩展操作(3)

3.扩展 代码生成 逻辑删除 枚举处理器 json处理器 配置加密 分页插件 3.1 代码生成 https://blog.csdn.net/weixin_41957626/article/details/132651552 下载下面的插件 红色的是刚刚生成的。 我觉得不如官方的那个好用&#xff0c;唯一的好处就是勾选的选项能够看的懂得。…...

react 中 antd 的 样式和 tailwind 样式冲突

问题原因&#xff1a;在使用 tailwindcss 时&#xff0c;会导入大量的 tailwindcss 默认属性&#xff0c;而默认样式中 button, [typebutton] 包含了 background-color: transparent; 从而导致 antd Button 按钮背景色变成透明。解决办法&#xff1a;禁止 tailwindcss 的默认属…...

获取该虚拟机的所有权失败,主机上的某个应用程序正在使用该虚拟机

点击“openstack-controller”虚机 打开出现如下错误&#xff0c;点击“获取所有权” 点击“取消” 这时候不要删除虚拟机&#xff0c;这种错误一般是由于虚拟机没有正常关闭引起的。 找到openstack-controller的虚拟磁盘文件及配置文件存放的位置&#xff0c;删除openstack-…...

2024届校招-Java开发笔试题-S4卷

有三种题型&#xff1a;单项选择题&#xff08;10道&#xff09;、不定项选择题&#xff08;10道&#xff09;、编程题&#xff08;3道&#xff09; 下面是一些回忆的题目&#xff1a; 1.哪种设计模式将对象的创建与使用分离&#xff0c;通过工厂类创建对象 答&#xff1a;工…...

数据分析面试题(2023.09.08)

数据分析流程 总体分为四层&#xff1a;需求层、数据层、分析层和结论层 一、统计学问题 1、贝叶斯公式复述并解释应用场景 公式&#xff1a;P(A|B) P(B|A)*P(A) / P(B)应用场景&#xff1a;如搜索query纠错&#xff0c;设A为正确的词&#xff0c;B为输入的词&#xff0c;那…...

jenkins 报错fatal:could not read Username for ‘XXX‘:No such device or address

#原因&#xff1a;机器做迁移&#xff0c;或者断电&#xff0c;遇到突发情况 #解决&#xff1a; 一.排查HOME和USER环境变量 可以在项目执行shell脚本的时候echo $HOME和USER 也可以在构建记录位置点击compare environment 对比两次构建的环境变量 二.查看指定节点的git凭证 查…...

LRU算法之我见

文章目录 一、LRU算法是什么&#xff1f;二、使用原理三、代码实现总结 一、LRU算法是什么&#xff1f; LRU算法又称最近最少使用算法&#xff0c;它是是大部分操作系统为最大化页面命中率而广泛采用的一种页面置换算法。是一种缓存淘汰策略&#xff0c;根据使用频率来淘汰无用…...

可靠性+灵活性:电力载波技术在楼宇自控中的核心价值

可靠性灵活性&#xff1a;电力载波技术在楼宇自控中的核心价值 在智能楼宇的自动化控制中&#xff0c;电力载波技术&#xff08;PLC&#xff09;凭借其独特的优势&#xff0c;正成为构建高效、稳定、灵活系统的核心解决方案。它利用现有电力线路传输数据&#xff0c;无需额外布…...

定时器任务——若依源码分析

分析util包下面的工具类schedule utils&#xff1a; ScheduleUtils 是若依中用于与 Quartz 框架交互的工具类&#xff0c;封装了定时任务的 创建、更新、暂停、删除等核心逻辑。 createScheduleJob createScheduleJob 用于将任务注册到 Quartz&#xff0c;先构建任务的 JobD…...

从零开始打造 OpenSTLinux 6.6 Yocto 系统(基于STM32CubeMX)(九)

设备树移植 和uboot设备树修改的内容同步到kernel将设备树stm32mp157d-stm32mp157daa1-mx.dts复制到内核源码目录下 源码修改及编译 修改arch/arm/boot/dts/st/Makefile&#xff0c;新增设备树编译 stm32mp157f-ev1-m4-examples.dtb \stm32mp157d-stm32mp157daa1-mx.dtb修改…...

Go 并发编程基础:通道(Channel)的使用

在 Go 中&#xff0c;Channel 是 Goroutine 之间通信的核心机制。它提供了一个线程安全的通信方式&#xff0c;用于在多个 Goroutine 之间传递数据&#xff0c;从而实现高效的并发编程。 本章将介绍 Channel 的基本概念、用法、缓冲、关闭机制以及 select 的使用。 一、Channel…...

免费数学几何作图web平台

光锐软件免费数学工具&#xff0c;maths,数学制图&#xff0c;数学作图&#xff0c;几何作图&#xff0c;几何&#xff0c;AR开发,AR教育,增强现实,软件公司,XR,MR,VR,虚拟仿真,虚拟现实,混合现实,教育科技产品,职业模拟培训,高保真VR场景,结构互动课件,元宇宙http://xaglare.c…...

4. TypeScript 类型推断与类型组合

一、类型推断 (一) 什么是类型推断 TypeScript 的类型推断会根据变量、函数返回值、对象和数组的赋值和使用方式&#xff0c;自动确定它们的类型。 这一特性减少了显式类型注解的需要&#xff0c;在保持类型安全的同时简化了代码。通过分析上下文和初始值&#xff0c;TypeSc…...

数据结构:递归的种类(Types of Recursion)

目录 尾递归&#xff08;Tail Recursion&#xff09; 什么是 Loop&#xff08;循环&#xff09;&#xff1f; 复杂度分析 头递归&#xff08;Head Recursion&#xff09; 树形递归&#xff08;Tree Recursion&#xff09; 线性递归&#xff08;Linear Recursion&#xff09;…...

jdbc查询mysql数据库时,出现id顺序错误的情况

我在repository中的查询语句如下所示&#xff0c;即传入一个List<intager>的数据&#xff0c;返回这些id的问题列表。但是由于数据库查询时ID列表的顺序与预期不一致&#xff0c;会导致返回的id是从小到大排列的&#xff0c;但我不希望这样。 Query("SELECT NEW com…...

qt+vs Generated File下的moc_和ui_文件丢失导致 error LNK2001

qt 5.9.7 vs2013 qt add-in 2.3.2 起因是添加一个新的控件类&#xff0c;直接把源文件拖进VS的项目里&#xff0c;然后VS卡住十秒&#xff0c;然后编译就报一堆 error LNK2001 一看项目的Generated Files下的moc_和ui_文件丢失了一部分&#xff0c;导致编译的时候找不到了。因…...

高保真组件库:开关

一:制作关状态 拖入一个矩形作为关闭的底色:44 x 22,填充灰色CCCCCC,圆角23,边框宽度0,文本为”关“,右对齐,边距2,2,6,2,文本颜色白色FFFFFF。 拖拽一个椭圆,尺寸18 x 18,边框为0。3. 全选转为动态面板状态1命名为”关“。 二:制作开状态 复制关状态并命名为”开…...