Spring AOP


什么是 AOP?

  • 面向切面编程(Aspect Oriented Programming,简称 AOP),是一种编程思想,可以说是面向对象编程(Object Oriented Programing,简称 OOP)的补充和完善。它是一种可以在运行时或者编译期、类加载期将代码切入到类的指定方法或位置上的编程思想。

AOP 常见使用场景

  • 日志场景,方法前后打印相关信息,比如入参、出参、执行时间等
  • 统计场景
    • 方法调用次数
    • 执行异常次数
    • 数据抽样
    • 数值累加
  • 安全场景
    • 熔断,如:Netflix Hystrix
    • 限流和降级,如:Alibaba Sentinel
    • 认证和授权,如:Spring Security
    • 监控,如:JMX
  • 性能场景
    • 缓存,如:Spring Cache
    • 超时控制

什么是连接点、切点、增强、引介、切面、目标、代理、织入?

  • 连接点(Joinpoint)
    • 程序执行的某个特定位置(如:某个方法调用前、调用后,方法抛出异常后)。一个类或一段程序代码拥有一些具有边界性质的特定点,这些代码中的特定点就是连接点。Spring 仅支持方法的连接点。
  • 切点(Pointcut)
    • 如果连接点相当于数据中的记录,那么切点相当于查询条件,一个切点可以匹配多个连接点。Spring AOP 的规则解析引擎负责解析切点所设定的查询条件,找到对应的连接点。
  • 增强(Advice)
    • 增强是织入到目标类连接点上的一段程序代码。
  • 引介(Introduction)
    • 引介是一种特殊的增强,它为类添加一些属性和方法。这样,即使一个业务类原本没有实现某个接口,通过引介功能,可以动态的为该业务类添加接口的实现逻辑,让业务类成为这个接口的实现类。
  • 切面(Aspect)
    • 切面是由切点(Pointcut)和增强(Advice)组成的,它包括了对横切关注功能的定义,也包括了对连接点的定义。
  • 目标(Target)
    • 即被通知的对象,如果没有 AOP,那么通知的逻辑就要写在目标对象中,有了 AOP 之后它可以只关注自己要做的事。
  • 代理(Proxy)
    • 代理是通知目标对象后创建的对象,从客户端的角度看,代理对象和目标对象是一样的。
  • 织入(Weaving)
    • 织入是将增强添加到目标类具体连接点上的过程,AOP有三种织入方式
    • ①编译期织入:需要特殊的 Java 编译器(例如 AspectJ 的 ajc)
    • ②类加载期织入:要求使用特殊的类加载器,在装载类的时候对类进行增强
    • ③运行时织入:在运行时为目标类生成代理实现增强。
    • Spring 采用了动态代理的方式实现了运行时织入,而 AspectJ 采用了编译期织入和装载期织入的方式。

有哪些类型的通知(Advice),以及它们的 XML 标签和注解实现是什么?

通知类型英文描述注解实现XML 标签
环绕通知Around Advice@Around<aop:around/>
前置通知Before Advice@Before<aop:before/>
后置通知After Advice@After<aop:after/>
成功执行方法之后的返回通知AfterReturning Advice@AfterReturning<aop:after-returning/>
抛出异常之后的异常通知AfterThrowing Advice@AfterThrowing<aop:after-throwing/>

AOP 有哪些实现方式?

实现 AOP 的技术,主要分为两大类:

  • 静态代理 - 指使用 AOP 框架提供的命令进行编译,从而在编译阶段就可生成 AOP 代理类,因此也称为编译时增强;
    • 编译时编织(特殊编译器实现);
    • 类加载时编织(特殊的类加载器实现)。
  • 动态代理 - 在运行时在内存中“临时”生成 AOP 动态代理类,因此也被称为运行时增强。
    • JDK 动态代理:通过反射来接收被代理的类,并且要求被代理的类必须实现一个接口。JDK 动态代理的核心是 InvocationHandler 接口和 Proxy 类 。
    • CGLIB 动态代理:如果目标类没有实现接口,那么 Spring AOP 会选择使用 CGLIB 来动态代理目标类 。CGLIB(Code Generation Library),是一个代码生成的类库,可以在运行时动态的生成某个类的子类,注意,CGLIB 是通过继承的方式做的动态代理,因此如果某个类被标记为 final ,那么它是无法使用 CGLIB 做动态代理的。

Spring AOP 和 AspectJ AOP 有什么区别?

  • AspectJ 是 AOP 完整实现,Spring AOP 则是部分实现,Spring AOP 需要依赖 IoC 容器来管理,并且只能作用于 Spring 容器,使用纯Java代码实现。
  • Spring AOP 基于动态代理来实现,如果使用接口的,用 JDK 动态代理实现,如果是方法则使用 CGLIB 动态代理实现。
  • AspectJ 属于静态织入,包括编译期织入和类加载时织入。
  • Spring AOP 仅支持方法级别的 Pointcuts。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

✦昨夜星辰✦

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值