SpringAOP的实现原理是动态代理,最终放入容器的是代理类的对象,而不是Bean本身的对象。
AOP增强定位于Bean生命周期当中的后置处理操作BeanPostProcessor
,如下图所示
后置处理器AnnotationAwareAspectJAutoProxyCreator
专门用来处理AOP增强,是BeanPostProcessor
的子接口。
当Bean对象初始化完成之后,postProcessAfterInitialization
方法会判断该Bean是否注册了切面,若是,则生成代理对象注入到容器中
接下来让我们从@EnableAspectJAutoProxy注解入手,去深入分析AOP的源码
- 开启@EnableAspectJAutoProxy,注入Bean的后置处理器
AnnotationAwareAspectJAutoProxyCreator
- 找被切面增强的Advisor
- org.springframework.aop.framework.autoproxy.AbstractAdvisorAutoProxyCreator#findEligibleAdvisors
- org.springframework.aop.aspectj.annotation.AnnotationAwareAspectJAutoProxyCreator#findCandidateAdvisors
- org.springframework.aop.support.AopUtils#findAdvisorsThatCanApply
- 代理对象的创建
- org.springframework.aop.framework.autoproxy.AbstractAutoProxyCreator#postProcessAfterInitialization
- org.springframework.aop.framework.autoproxy.AbstractAutoProxyCreator#wrapIfNecessary
- org.springframework.aop.framework.autoproxy.AbstractAutoProxyCreator#createProxy
- org.springframework.aop.framework.JdkDynamicAopProxy#getProxy(java.lang.ClassLoader)
- 代理方法的执行
- org.springframework.aop.framework.JdkDynamicAopProxy#invoke
- org.springframework.aop.framework.ReflectiveMethodInvocation#proceed,interceptorsAndDynamicMethodMatchers中第一个advice为org.springframework.aop.interceptor.ExposeInvocationInterceptor。
- 拦截器链MethodInterceptor
- ExposeInvocationInterceptor
- 环绕通知的执行
- 前置通知的执行
- 后置通知的执行
- 返回后通知的执行
- 异常通知的执行
开启后置处理增强器
@EnableAspectJAutoProxy注解用于开启AOP功能,它使用@Import注解向Spring容器中注入了一个类型为AspectJAutoProxyRegistrar
的Bean
AspectJAutoProxyRegistrar
实现了ImportBeanDefinitionRegistrar
接口,而ImportBeanDefinitionRegistrar
是spring提供的扩展点之一,主要用来向容器中注入BeanDefinition
,Spring会根据BeanDefinion来生成Bean。通过AspectJAutoProxyRegistrar
向IOC容器中注册一个AnnotationAwareAspectJAutoProxyCreator
组件
找被切面增强的Advisor
…代理对象的创建
…代理方法的执行
这个代理对象创建完以后,IOC容器也就创建完了。接下来,便要来执行目标方法了。
此时,其实是代理对象来执行目标方法
使用CglibAopProxy类的intercept()方法来拦截目标方法的执行,拦截的过程如下:
得到目标方法的拦截器链,所谓的拦截器链其实就是每一个通知方法又被包装为了方法拦截器,即MethodInterceptor
利用拦截器的链式机制,依次进入每一个拦截器中进行执行
最终,整个的执行效果就会有两套:
目标方法正常执行:前置通知→目标方法→后置通知→返回通知
目标方法出现异常:前置通知→目标方法→后置通知→异常通知
[
](https://blog.csdn.net/yerenyuan_pku/article/details/111677048)