Spring之AOP的实现

AOC概述   

 AOP(Aspect Oriented Programming),即面向切面编程,可以说是OOP(Object Oriented Programming,面向对象编程)的补充和完善。OOP引入封装、继承、多态等概念来建立一种对象层次结构,用于模拟公共行为的一个集合。不过OOP允许开发者定义纵向的关系,但并不适合定义横向的关系,例如日志功能。日志代码往往横向地散布在所有对象层次中,而与它对应的对象的核心功能毫无关系对于其他类型的代码,如安全性、异常处理和透明的持续性也都是如此,这种散布在各处的无关的代码被称为横切(cross cutting),在OOP设计中,它导致了大量代码的重复,而不利于各个模块的重用。

    AOP技术恰恰相反,它利用一种称为"横切"的技术,剖解开封装的对象内部,并将那些影响了多个类的公共行为封装到一个可重用模块,并将其命名为"Aspect",即切面。所谓"切面",简单说就是那些与业务无关,却为业务模块所共同调用的逻辑或责任封装起来,便于减少系统的重复代码,降低模块之间的耦合度,并有利于未来的可操作性和可维护性。

    使用"横切"技术,AOP把软件系统分为两个部分:核心关注点横切关注点。业务处理的主要流程是核心关注点,与之关系不大的部分是横切关注点。横切关注点的一个特点是,他们经常发生在核心关注点的多处,而各处基本相似,比如权限认证、日志、事物。AOP的作用在于分离系统中的各种关注点,将核心关注点和横切关注点分离开来。

014146_XGt5_1765168.png

Advice通知

    Advice定义在连接点做什么,为切面增强提供织入接口。它主要描述Spring AOP围绕方法调用而注入的切面行为。

增强(advice)主要包括如下五种类型 
1. 前置增强(BeforeAdvice):在目标方法执行前实施增强 
2. 后置增强(AfterReturningAdvice):在目标方法执行后实施增强 
3. 环绕增强(MrthodInterceptor):在目标方法执行前后实施增强 
4. 异常抛出增强(ThrowsAdvice):在目标方法抛出异常后实施增强 
5. 引介增强(IntroductionIntercrptor):在目标类中添加一些新的方法和属性

Pointcut切点

    Pointcut(切点)决定Advice通知应该作用于哪个连接点。

Advisor通知器

    完成对目标方法的切面增强设计(Advice)和关注点的设计(Pointcut)以后,需要一个对象把它们结合在一块,完成这个作用的就是Advisor(通知器)。Advisor定义应该使用哪个通知并在哪个关注点使用它,将Advice注入程序中Pointcut位置。

AopProxy对象建立

    通过配置和调用spring的ProxyFactoryBean来完成代理对象的生成,可以使用JDK的Proxy和CGLIB两种方式生成。

024756_Epg5_1765168.png

ProxyFactoryBean生成AopProxy代理对象

    ProxyFactoryBean是一个FactoryBean, 用来配置目标对象和切面行为。在ProxyFactoryBean中, 通过interceptorNames属性来配置已经定义好的通知器Advisor, 还需要为target目标对象生成Proxy代理对象,从而为AOP横切面编制好准备工作。

    在FactoryBean中获取对象, 是以getObject()方法作为入口完成的,也是通过该方法对target目标对象进行增强处理来为AOP功能的实现提供服务。getObject方法首先对通知链进行初始化,通知链封装了一系列拦截器,这些拦截器都在配置中读取。

111707_7sQJ_1765168.png

143817_9yJJ_1765168.png

Spring AOP拦截器调用实现

    Spring AOP通过JDK的Proxy方式或CGLIB方式生成代理对象的时候,相关的拦截器已经配置到代理对象中去了,拦截器在代理对象中起作用是通过对这些方法的回调来完成的。

    JDK的 Proxy来生成代理对象,需要通过Invocationhandler来设置拦截器回调;CGLIB生成代理对象,通过DynamicAdvisedInterceptor来完成回调。

JdkDynamicAopProxy的invoke拦截

    invoke方法是JDK Proxy代理对象进行拦截回调的入口。invoke方法包含了一个完整的拦截链对目标对象的拦截过程,比如获得拦截器链并对拦截器链中的拦截器进行配送,逐个运行拦截器链中的拦截增强,直到最后对目标对象方法的运行等。

Cglib2AopProxy的intercept拦截

    Cglib2AopProxy回调是在DynamicAdvisedInterceptor对象中实现,回调的实现在intercept方法中。实现类似上边的invoke方法。

AOP拦截器链的调用

    AOP目标对象的增强封装在AOP拦截器链中,由一个个具体的拦截器来完成。两种代理对象对拦截器链的调用都是在ReflectiveMethodInvocation中通过proceed方法实现。在proceed方法中,先进行判断,如果已经运行到拦截器链的末尾,就直接调用目标方法的实现方法;否则沿着拦截器链, 得到下一个拦截器,通过这个拦截器进行matches判断是否适用于横切增强的集合,如果是,从拦截器中得到通知器,并启动通知器的invoke方法进行切面增强,这个过程会迭代调用proceed方法。

配置通知器

    advisor通知器的取得是委托给IOC容器完成的。ProxyFactoryBean通过回调容器的getBean去获取配置在Bean定义文件中的通知器。ProxyFactoryBean给出通知器的名字, 这些名字配置在interceptorNames的List中配置好。在IOC对FactoryBean进行依赖注入时,会直接注入到FactoryBean的interceptorNames的属性中。完成这个过程,ProxyFactoryBean就获得了配置的通知器,为未完成切面增强做好了准备。

 

 

 

 

 

 

转载于:https://my.oschina.net/u/1765168/blog/1801919

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值