Spring AOP原理
2022-01-13 10:23:23 1 举报
Spring AOP原理
作者其他创作
大纲/内容
createBean()
目标方法的执行
代码原理研究:看给容器中注册了什么组件,这个组件什么时候工作,包括这个组件工作时候的功能
finishBeanFactoryInitialization
proxyFactory.addAdvisors
AbstractAutowireCapableBeanFactory#applyBeanPostProcessorsBeforeInstantiation拿到所有后置处理器,如果是InstantiationAwareBeanPostProcessor; 就执行postProcessBeforeInstantiation
没有拦截器链,直接执行目标方法
chain = this.advised.getInterceptorsAndDynamicInterceptionAdvice
给增强器排序
根据ProxyFactory对象获取目标方法将要执行的拦截器链
传入主配置类,创建IOC容器
如果有拦截器链,把需要执行的目标对象,目标方法,拦截器链等信息传入创建一个CglibMethodInvocation对象,并调用proceed()方法获取返回值
findCandidateAdvisors
initializeBean
true
AopConfigUtils#registerAspectJAnnotationAutoProxyCreatorIfNecessary(registry)
继承树
获取到能在bean使用的增强器
每个bean创建之前,调用postProcessBeforeInstantiation()关心MathCalculator和LogAspect的创建
否
保存当前bean在advisedBeans中
extends
判断拦截器链chain isEmpty()
implements
AspectJAutoProxyRegistrar implementsImportBeanDefinitionRegistrar
1)@EnableAspectJAutoProxy开启AOP功能2)@EnableAspectJAutoProxy会给容器中注册一个AnnotationAwareAspectJAutoProxyCreator3)AnnotationAwareAspectJAutoProxyCreator是一个后置处理器4)容器的创建流程: 1)registerBeanPostProcessors()注册后置处理器;AnnotationAwareAspectJAutoProxyCreator创建对象 2)finishBeanFactoryInitialization()初始化剩余的单实例bean 1)创建业务逻辑组件和切面组件 2)AnnotationAwareAspectJAutoProxyCreator拦截组件的创建过程 3)组件创建完之后,判断组件是否需要增强 是:切面的通知方法,包装成增强器(Advisor);给业务逻辑组件创建一个代理对象(cglib)5)、执行目标方法: 1)、代理对象执行目标方法 2)、CglibAopProxy.intercept(); 1)、得到目标方法的拦截器链(增强器包装成拦截器MethodInterceptor) 2)、利用拦截器的链式机制,依次进入每一个拦截器进行执行; 3)、效果: 正常执行:前置通知-》目标方法-》后置通知-》返回通知 出现异常:前置通知-》目标方法-》后置通知-》异常通知
AopConfigUtils #registerOrEscalateApcAsRequired
AspectJAwareAdvisorAutoProxyCreator
this.buildAdvisors()
ProxyProcessorSupport
false
this.advisedBeans.containsKey(cacheKey)
AbstractAutowireCapableBeanFactory#createBean
保存到proxyFactory
super.proceed()
this.advisedBeans.put()
注册配置类
如果没有拦截器执行执行目标方法,或者拦截器的索引和拦截器数组-1大小一样(指定到了最后一个拦截器)执行目标方法
beanFactory.addBeanPostProcessor(postProcessor);
registry.registerBeanDefinition(\"xxx.internalAutoProxyCreator\
创建名为internalAutoProxyCreator的AnnotationAwareAspectJAutoProxyCreator对象
MathCalculator创建完成
AbstractAutoProxyCreator#setBeanFactory()AbstractAutoProxyCreator#postProcessBeforeInstantiation(后置处理器)AbstractAutoProxyCreator#postProcessAfterInitialization(后置处理器)AbstractAdvisorAutoProxyCreator#setBeanFactory()--->initBeanFactoryAnnotationAwareAspectJAutoProxyCreator#initBeanFactory
AnnotationAwareAspectJAutoProxyCreator
getBean()->doGetBean()
sortAdvisors
this.registerBeanPostProcessors
是否包含internalAutoProxyCreator
beanFactory.getBean
1)、创建Bean的实例2)、populateBean;给bean的各种属性赋值3)、initializeBean:初始化bean;4)、BeanPostProcessor(AnnotationAwareAspectJAutoProxyCreator)创建成功;--》aspectJAdvisorsBuilder
1)、invokeAwareMethods():处理Aware接口的方法回调2)、applyBeanPostProcessorsBeforeInitialization():应用后置处理器的postProcessBeforeInitialization()3)、invokeInitMethods();执行自定义的初始化方法4)、applyBeanPostProcessorsAfterInitialization();执行后置处理器的postProcessAfterInitialization();
AbstractAdvisorAutoProxyCreator
判断当前bean是否在advisedBeans中(保存了所有需要增强bean)
AnnotationAwareAspectJAutoProxyCreator创建完成
return this.getObjectForBeanInstance
getAdvicesAndAdvisorsForBean
invocation = new NamedThreadLocal(\"Current AOP method invocation\");多个线程共享数据的invoke(this)就是执行MethodInvocation的procced()
在容器中注册AnnotationAwareAspectJAutoProxyCreatorBean定义信息
SmartInstantiationAwareBeanPostProcessor
sharedInstance = this.getSingleton(beanName);
sharedInstance!=null
完成BeanFactory初始化工作
是否需要跳过 1)、获取候选的增强器(切面里面的通知方法)【List<Advisor> candidateAdvisors】每一个封装的通知方法的增强器是 InstantiationModelAwarePointcutAdvisor; 判断每一个增强器是否是 AspectJPointcutAdvisor 类型的;返回true2)、永远返回false
findAdvisorsThatCanApply
CglibAopProcy.DynamicAdvisedInterceptor#intercept
postProcessBeforeInstantiation
【BeanPostProcessor是在Bean对象创建完成初始化前后调用的】【InstantiationAwareBeanPostProcessor是在创建Bean实例之前先尝试用后置处理器返回对象的】AnnotationAwareAspectJAutoProxyCreator在所有bean创建之前会有一个拦截,InstantiationAwareBeanPostProcessor,会调用postProcessBeforeInstantiation()
DefaultListableBeanFactory#preInstantiateSingletons
AbstractAutoProxyCreator
getSingleton()
findEligibleAdvisors
获取所有增强器(增强方法)
@EnableAspectJAutoProxy开启切面
AnnotationAwareAspectJAutoProxyCreator => InstantiationAwareBeanPostProcessor
this.register(componentClasses)
总结
执行效果正常执行:前置通知-》目标方法-》后置通知-》返回通知 出现异常:前置通知-》目标方法-》后置通知-》异常通知
@Import({AspectJAutoProxyRegistrar.class})
this.createProxy
希望后置处理器在此能返回一个代理对象;如果能返回代理对象就使用,如果不能就继续
调用容器刷新
PostProcessorRegistrationDelegate#registerBeanPostProcessors
for
this.getAdvicesAndAdvisorsForBean
链式获取每一个拦截器,拦截器执行invoke方法,每一个拦截器等待下一个拦截器执行完成返回以后再来执行;拦截器链的机制,保证通知方法与目标方法的执行顺序;
this.resolveBeforeInstantiation()
chain size=5[0]ExposeInvocationInterceptor[1]MethodBeforeAdviceInterceptor【MethodName:logStart】[2]AspectJAfterAdvice【MethodName:logEnd】[3]AfterReturningAdviceInterceptor【MethodName:logReturn】[4]AspectJAfterThrowingAdvice【MethodName:logException】
1、先获取ioc容器中已经定义了的需要创建对象的所有BeanPostProcessor beanFactory.getBeanNamesForType();2、给容器中加别的BeanPostProcessor beanFactory.addBeanPostProcessor();3、对实现了PriorityOrdered接口和Ordered接口以及其它的BeanPostProcessor以进行分类4、优先注册实现了PriorityOrdered接口的BeanPostProcessor ,其次注册实现了Ordered接口的BeanPostProcessor,最后注册其它的BeanPostProcessor5、AnnotationAwareAspectJAutoProxyCreator实现了Ordered接口,注册这个BeanPostProcessor,实际上就是创建这个对象,保存在容器中
判断当前bean是否是基础类型的Advice、Pointcut、Advisor、AopInfrastructureBean, 或者是否是切面(@Aspect)
关注后置处理器(在bean初始化完成前后做事情)(SmartInstantiationAwareBeanPostProcessor)自动装配beanFactory(BeanFactoryAware)
首先:配置解析
找到候选的增强器(找哪些通知方法是需要切入当前bean方法的)
如果当前bean需要增强,创建代理对象
AbstractAutoProxyCreator#postProcessAfterInitialization
this.wrapIfNecessary
this.refresh()
ReflectiveMethodInvocation.proceed
AspectJAutoProxyRegistrar#registerBeanDefinitions
new AnnotationConfigApplicationContext(MainConfigOfAOP.class)
BeanFactoryAware
收藏
0 条评论
下一页