news 2026/5/4 3:01:27

SpringAOP原理(代理模式)

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
SpringAOP原理(代理模式)

Spring AOP是基于动态代理来实现AOP的,动态代理又是代理模式的一种

什么叫代理模式

定义:为其他对象提供⼀种代理以控制对这个对象的访问.它的作⽤就是通过提供⼀个代理类,让我们在调⽤⽬标⽅法的时候,不再是直接对目标⽅法进行调用,而是通过代理类间接调用.

在某些情况下,⼀个对象不适合或者不能直接引⽤另⼀个对象,而代理对象可以在客⼾端和目标对象之间起到中介的作用

使用代理后:

生活中其实也存在着代理模式:

  • 艺人经纪⼈:光告商找艺⼈拍⼴告,需要经过经纪⼈,由经纪⼈来和艺⼈进行沟通.
  • 房屋中介:房屋进行租赁时,卖⽅会把房屋授权给中介,由中介来代理看房,房屋咨询等服务.
  • 经销商:⼚商不直接对外销售产品,由经销商负责代理销售.
  • 秘书/助理:合作伙伴找⽼板谈合作,需要先经过秘书/助理预约.

接下来我们来一起认识一下代理模式里的主要角色

  1. Subject:业务接⼝类.可以是抽象类或者接⼝(不⼀定有)
  2. RealSubject:业务实现类.具体的业务执⾏,也就是被代理对象.
  3. Proxy:代理类.RealSubject的代理

如果看成租房:

Subject:就是提前定了义房东做的事情,交给中介代理,也是中介要做的事情
RealSubject:房东
Proxy:中介

代理模式可以在不修改被代理对象的基础上,通过扩展代理类,进行⼀些功能的附加与增强.

根据代理的创建时期,代理模式分为静态代理和动态代理.

  • 静态代理:由程序员创建代理类或特定⼯具⾃动⽣成源代码再对其编译,在程序运⾏前代理类的
    .class⽂件就已经存在了.
  • 动态代理:在程序运⾏时,运⽤反射机制动态创建⽽成.

静态代理

静态代理: 在程序运⾏前,代理类的.class⽂件就已经存在了.(在出租房⼦之前,中介已经做好了相关的⼯作,就等租⼾来租房⼦了)

我们通过代码来加深理解.以房租租赁为例

1. 定义接⼝(定义房东要做的事情,也是中介需要做的事情)

2. 实现接⼝(房东出租房⼦)

3. 代理(中介,帮房东出租房⼦)

使用:

结果:

虽然静态代理也完成了对目标对象的代理,但是由于代码都写死了,对⽬标对象的每个⽅法的增强都是⼿动完成的,⾮常不灵活.所以⽇常开发⼏乎看不到静态代理的场景

如果目标对象新增其他业务,则需要我们手动进行修改,同样的,如果有新增接(Subject)和业务实现类(RealSubject),也需要对每⼀个业务实现类新增代理类(Proxy).

既然代理的流程是⼀样的,有没有⼀种办法,让他们通过⼀个代理类来实现呢?

这就需要⽤到动态代理技术了

动态代理

相比于静态代理来说,动态代理更加灵活.

我们不需要针对每个目标对象都单独创建⼀个代理对象,而是把这个创建代理对象的⼯作推迟到程序运行时由JVM来实现.也就是说动态代理在程序运行时,根据需要动态创建⽣成.

比如房屋中介,我不需要提前预测都有哪些业务,而是业务来了我再根据情况创建.

Java也对动态代理进⾏了实现,并给我们提供了⼀些API,常见的实现方式有两种:

  1. JDK动态代理
  2. CGLIB动态代理

动态代理在我们⽇常开发中使⽤的相对较少,但是在框架中⼏乎是必⽤的⼀⻔技术.学会了动态代理 之后,对于我们理解和学习各种框架的原理也⾮常有帮助

JDK动态代理

JDK动态代理类实现步骤

1.定义⼀个接⼝及其实现类(静态代理中的 HouseSubject 和 RealHouseSubject )
2.⾃定义 InvocationHandler 并重写 invoke ⽅法,在 invoke ⽅法中我们会调⽤⽬标⽅法(被代理类的⽅法)并⾃定义⼀些处理逻辑
3.通过 javaProxy.newProxyInstance(ClassLoader loader,Class<?>[] interfaces,InvocationHandler h) ⽅法创建代理对象

在此之前,还是需要有房子和房东

下面我们来进行实现以下:

定义JDK动态代理类

实现 InvocationHandler 接⼝

创建⼀个代理对象并使用

对上述代码做一个简单的讲解:

1.InvocationHandler接是Java动态代理的关键接⼝之⼀,它定义了⼀个单⼀⽅法 invoke() ,用于处理被代理对象的方法调用.通过实现 InvocationHandler 接⼝,可以对被代理对象的方法进⾏功能增强.
2.Proxy 类中使⽤频率最高的⽅法是: newProxyInstance() ,这个⽅法主要⽤来⽣成⼀个代理对象

这个⽅法⼀共有3个参数:

  • Loader:类加载器,⽤于加载代理对象.
  • interfaces:被代理类实现的⼀些接⼝(这个参数的定义,也决定了JDK动态代理只能代理实现了接⼝的⼀些类)
  • h:实现了InvocationHandler接⼝的对象

CGLIB动态代理

JDK 动态代理有⼀个最致命的问题是其只能代理实现了接⼝的类.

有些场景下,我们的业务代码是直接实现的,并没有接⼝定义.为了解决这个问题,我们可以⽤CGLIB动
态代理机制来解决.

例如:Spring中的AOP模块中:如果⽬标对象实现了接⼝,则默认采⽤JDK动态代理,否则采⽤CGLIB动态代理.

CGLIB动态代理类实现步骤

  1. 定义⼀个类(被代理类)
  2. ⾃定义 MethodInterceptor 并重写 intercept ⽅法, intercept ⽤于增强⽬标⽅法,和JDK动态代理中的 invoke ⽅法类似
  3. 通过Enhancer类的create()创建代理类

接下来一起来看一下实一个简单的实现:

  • 1. 添加依赖

和JDK动态代理不同,CGLIB(Code Generation Library)实际是属于⼀个开源项⽬,如果你要使用它
的话,需要⼿动添加相关依赖

  • 2. ⾃定义CGLibMethodInterceptor(⽅法拦截器)

实现MethodInterceptor接口

  • 3. 创建代理类

  • 4. 运行

代码简单讲解如下:

  • CGLibMethodInterceptor和JDK动态代理中的 InvocationHandler 类似,它只定义了⼀个方法 intercept() ,用于增强目标⽅法
  • Enhancer.create()用来⽣成⼀个代理对象

JDK和CGLIB区别

  • JDK只能代理接口
  • CGLIB可以代理接口也可以代理类
版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/5/4 2:58:24

桌面/在线/小程序三种路线,2026年免费录音转文字工具怎么选?

同样是处理音频文件,用桌面软件和用微信小程序的体验差别比较大。前者需要下载安装、学习界面逻辑,后者搜一下就能用,等待时间也更短。如果你的需求很简单——比如临时转几段录音、快速提取视频文案,那小程序路线省事得多。本文主要拆解免费录音转文字工具的几种主流方案,重点讲…

作者头像 李华
网站建设 2026/5/4 2:58:23

录音转文字免费工具有哪些?免费录音转文字工具对比与推荐

开头做视频素材处理的时候,经常卡在一个问题:怎么把录音、视频里的人声快速提取成文字。大多数人默认想到的是找个桌面软件或者网页工具,但其实微信小程序里有个叫提词匠的工具在这块需求上效率比较高,下面会重点拆解它,因为它能覆盖大多数人的日常场景——无论是会议录音、课程…

作者头像 李华
网站建设 2026/5/4 2:57:47

5分钟搞定:BetterJoy让你的Switch手柄在PC上完美重生

5分钟搞定&#xff1a;BetterJoy让你的Switch手柄在PC上完美重生 【免费下载链接】BetterJoy Allows the Nintendo Switch Pro Controller, Joycons and SNES controller to be used with CEMU, Citra, Dolphin, Yuzu and as generic XInput 项目地址: https://gitcode.com/g…

作者头像 李华
网站建设 2026/5/4 2:55:26

Library Compiler:时序弧建模与约束全解析(三)

相关阅读 Library Compilerhttps://blog.csdn.net/weixin_45791458/category_13154201.html?spm1001.2014.3001.5482 描述三态时序弧 三态时序弧用于描述单元中的三态输出引脚。 描述三态关闭时序弧 在定义三态引脚时&#xff0c;要指定一个三态关闭时序弧&#xff0c;需要执…

作者头像 李华
网站建设 2026/5/4 2:45:26

基于开源框架的AI智能体开发实战:从架构设计到工程实现

1. 项目概述&#xff1a;从开源社区到智能体英雄的诞生最近在GitHub上看到一个挺有意思的项目&#xff0c;叫agentheroes/agentheroes。光看这个名字&#xff0c;你可能会觉得有点中二&#xff0c;像是某个游戏或者漫画的粉丝项目。但点进去之后&#xff0c;你会发现&#xff0…

作者头像 李华