AOP分析的起点
当引入AOP的场景启动器,@EnableAspectJAutoProxy引入AspectJAutoProxyRegistrar注册器。
它会去注册类为AnnotationAwareAspectJAutoProxyCreator的beandefinition。
AnnotationAwareAspectJAutoProxyCreator是bean后处理器,spring创建bean时,会在bean初始化前,以及bean初始化后,执行相应的处理。
目标初始化后,会调用其postProcessAfterInitialization,这也是AOP逻辑分析的起点。
获取所有的增强
其实目标bean初始化前,在postProcessBeforeInstantiation方法里,会判断是不是应当跳过增强时,由于我们声明过一个切面,此时就会根据该切面尝试获取Advisor。(会判断有没有@Advice注解)。并添加到缓存中。
1、获取增强方法时,会排除掉@PointCut注解对应的方法。会把切点信息即@PointCut信息,封装为AspectJExpressionPointcut,然后根据切点信息和增强方法信息构建为一个增强器。(每一个增强方法对应一个增强器)。
所有的增强器都由Advisor的实现类InstantiationModelAwarePointcutAdvisorImpl统一封装。
2、在构建InstantiationModelAwarePointcutAdvisorImpl时,只是简单的将信息封装在类实例中。但要明白一点的是,不同的增强器所体现的逻辑是不同的,它们的增强的位置不同,也表示它们使用的肯定是不同的增强器。决定它们不同的是在该类的构造器的instantiateAdvice方法。
找出适合于目标bean的增强
如果我们声明了事务,切面中有前置通知、后置通知、环绕通知的话,此时就有四个增强器。
为什么说通知也是增强器呢?是因为此时每个增强器里,封装着切入点和通知对象。
之前事务增强的PointCut是判断类或方法上是否有@Transactional注解。而现在需要根据切点的方法表达式去和目标类以及它的接口的所有方法进行比对。(若比对则认为成功切人,返回对应增强器)
这里使用JDK的动态代理方式来分析AOP的实现过程。
1、创建代理对象
会把拦截器Interceptor统一转换为Advice,并连同刚刚获得可以应用目标bean的增强器Advisor,一同记录在ProxyFactory代理工厂中。
接着ProxyFactory选择一种合适的方式去创建代理对象。下面来看看JDK动态代理时,AOP的实现过程。
JdkDynamicAopProxy实现InvocationHandler,当代理对象调用方法时,则会调用invoke。
在invoke中,有两个关键的步骤。
1、获取适合目标bean的Advice
之前是通过PointCut方法表达式,来找到可以增强的增强器。现在是获取增强器的通知。
后回通知AspectJAfterReturningAdvice,实现AfterReturningAdvice
前置通知:AspectJMethodBeforeAdvice,实现MethodBeforeAdvic
环绕通知:AspectJAroundAdvice,同时实现MethodInterceptor和Advice。
后置通知:AfterReturningAdvice,实现Advice
2、执行拦截器链
有关责任链的调度。ReflectiveMethodInvocation就如同servlet中的FilterChain。
网友评论