Spring注解学习_AOP原理3_AnnotationAwareAspectJAutoProxyCreator的作用

  1. AnnotationAwareAspectJAutoProxyCreator的作用:

AnnotationAwareAspectJAutoProxyCreator的作用:

  1. 每一个Bean创建之前,调用postProcessBeforeInstantiation(beanClass, beanName) 。我们重点关注前面文章中的自定义的业务逻辑类MathCalculator和LogAspect的创建流程:

    1. 判断当前Bean是否在advisedBeans中(保存了所有需要增强的Bean)

    2. 判断当前Bean是否是基础类型的:实现了Advice、PointCut、Advisor、AopInfrastructureBean接口,或者是否为切面(@Aspect)

      image-20200406043328824

      image-20200406043456921

      image-20200406043944483

    3. 判断当前Bean是否需要跳过:shouldSkip():

      • 获取候选的增强器(切面里的通知方法)【List candidateAdvisors】

        每一个封装的通知方法的增强器的类型为:InstantationModelAwarePointcutAdvisor

      • 遍历候选增强器,如果其为AspectJPointAdvisor,返回true

      • 调用父类的shouldSkip(直接返回false)

  2. 创建对象:

    AbstractAutoProxyCreator中:初始化后处理postProcessAfterInitialization:调用 wrapIfNecessary 方法,如果需要则返回包装Bean

    image-20200406050013338

    • 获取当前Bean的通知方法和增强器:getAdvicesAndAdvisorsForBean( ) --> findEligibleAdvisors( )

      • 找到能在当前bean使用的所有候选增强器(哪些通知方法是需要切入到当前bean方法的)

        image-20200406053341881

        image-20200406053707946

      • 找到能在当前Bean使用的增强器:

        image-20200406054403787

      • 给增强器排序

    • 保存当前bean在advisedBeans中

      image-20200406055744786

    • 如果当前bean需要增强,创建当前bean的代理对象:

      • 获取所有增强器(通知方法)
      • 保存到proxyFactory
      • 创建代理对象:proxyFactory.getProxy(),用代理工厂来创建并得到代理对象
    • 给容器返回当前组件增强后的代理对象

    • 以后容器中获取到的就是这个组建的代理对象,执行目标方法的时候,代理对象就会执行通知方法的流程

  3. 目标方法的执行

    容器中保存了组件的代理对象(本例MathCalculator为CgLib增强后的代理对象),这个对象里面保存了详细信息,如增强器、目标对象等。我们分析Cglib代理对象如何执行目标方法:

    1. CglibAopProxy.intercept() : 拦截目标方法的执行

    2. 根据ProxyFactory对象获取将要执行的目标方法的拦截器链:

      List<Object> chain = this.advised.getInterceptorsAndDynamicInterceptionAdvice(method, rootClass);

      • List<Object> chain 保存所有拦截器,包括:一个默认的ExposeInvocationInterceptor和本例中我们在切面中自定义的四个增强器(@Befor、@After、@AfterReturning、@AfterThrowing)

      • 遍历所有增强器,将其转为interceptor:register.getInterceptors(advisor);

      • 将增强器转为List<MethodIinterceptor>,转化完成后返回该数组。 :

        如果是MethodInterceptor,直接加入到集合中

        如果不是,使用AdvisorAdapter将增强器转为MethodInterceptor

    3. 如果没有拦截器链,直接执行目标方法:

      拦截器链:每一个通知方法又被包装为方法拦截器,利用MethodInterceptor机制

    4. 如果有拦截器链,把需要执行的目标对象,目标方法,拦截器等信息作为参数传入,创建一个cglibMethodInvocation对象,并调用这个对象的proceed() 方法

      Object retVal = new CglibMethodInvocation(proxy, target, method, args, targetClass, chain, methodProxy).proceed();
      
    5. 拦截器链的触发过程

      如果没有拦截器执行目标方法,或者拦截器的索引和拦截器数组-1大小一样(指定到了最后一个拦截器),执行目标方法


转载请注明来源,欢迎对文章中的引用来源进行考证,欢迎指出任何有错误或不够清晰的表达,邮件至 708801794@qq.com

文章标题:Spring注解学习_AOP原理3_AnnotationAwareAspectJAutoProxyCreator的作用

文章字数:773

本文作者:梅罢葛

发布时间:2020-04-06, 22:30:57

最后更新:2020-04-06, 22:36:00

原始链接:https://qiurungeng.github.io/2020/04/06/Spring%E6%B3%A8%E8%A7%A3%E5%AD%A6%E4%B9%A0-AOP%E5%8E%9F%E7%90%863-AnnotationAwareAspectJAutoProxyCreator%E7%9A%84%E4%BD%9C%E7%94%A8/
目录
×

喜欢就点赞,疼爱就打赏