乐趣区

关于aop:Spring-AOP原理上

SpringAOP 工作原理 - 上

作为 Spring 体系里的大块头,AOP 用起来是很爽,然而问你它是怎么实现的,你就懵逼。嘿嘿嘿 ~

还是从 SpringBoot 的启动流程来讲起,看看定义切面后的启动流程。

先看咱们的测试例子:

TestController.java :

LogAspect.java :

接下来,从启动流程看,TestController 和 LogAspect 是怎么创立的。

咱们找到 AbstractAutowireCapableBeanFactory#initializeBean() 办法,如图:

别问我怎么找到这个办法的,我不会通知你是打了九九八十一个断点调进去的 =。=

进入 applyBeanPostProcessorsAfterInitialization(wrappedBean, beanName) 办法,看下参数:

遍历到 AnnotationAwareAspectJAutoProxyCreator 这个 processor 的时候,debug 进去,能够看到:

这个 wrapIfNecessary() 办法就很要害了,再点进去:

能够看到这一步里,先是找到所有的告诉器(拦截器或者增强器),而后接下来创立 proxy:

点击 createProxy(),进入,看外围代码代码:

protected Object createProxy(Class<?> beanClass, @Nullable String beanName,
            @Nullable Object[] specificInterceptors, TargetSource targetSource) {

        ……

        ProxyFactory proxyFactory = new ProxyFactory();
        proxyFactory.copyFrom(this);

        ……

        Advisor[] advisors = buildAdvisors(beanName, specificInterceptors);
        proxyFactory.addAdvisors(advisors);
        proxyFactory.setTargetSource(targetSource);
        customizeProxyFactory(proxyFactory);

        proxyFactory.setFrozen(this.freezeProxy);
        if (advisorsPreFiltered()) {proxyFactory.setPreFiltered(true);
        }

        ClassLoader classLoader = getProxyClassLoader();
        if (classLoader instanceof SmartClassLoader && classLoader != beanClass.getClassLoader()) {classLoader = ((SmartClassLoader) classLoader).getOriginalClassLoader();}
        return proxyFactory.getProxy(classLoader);
    }

能够看到,这里都是对 proxyFactory 进行设置的。点击 proxyFactory.getProxy(classLoader),始终追到

DefaultAopProxyFactory # createAopProxy(),这里就是创立代理的外围了:

public AopProxy createAopProxy(AdvisedSupport config) throws AopConfigException {
    // 如果开启了优化,或者 ProxyTargetClass 设置为 true,或者没有代理类要实现的接口
    if (config.isOptimize() || config.isProxyTargetClass() || hasNoUserSuppliedProxyInterfaces(config)) {// 如果 targetClass( 这里是指咱们调试的 TestController.class) 是接口或者代理类,则创立 jdk 动静代理,否则返回 cglib 代理
        if (targetClass.isInterface() || Proxy.isProxyClass(targetClass)) {return new JdkDynamicAopProxy(config);
        }
        return new ObjenesisCglibAopProxy(config);
        }
        else {return new JdkDynamicAopProxy(config);
        }
    }

createAopProxy() 之后是 getProxy(),以 CglibAopProxy#getProxy() 为例:

public Object getProxy(@Nullable ClassLoader classLoader) {

    try {
        ……
        // 配置 CGLIB 增强器
        Enhancer enhancer = createEnhancer();
        if (classLoader != null) {enhancer.setClassLoader(classLoader);
            enhancer.setSuperclass(proxySuperClass);

enhancer.setInterfaces(AopProxyUtils.completeProxiedInterfaces(this.advised));
          enhancer.setNamingPolicy(SpringNamingPolicy.INSTANCE);
            enhancer.setStrategy(new ClassLoaderAwareGeneratorStrategy(classLoader));
            // 获取代理的回调办法
            Callback[] callbacks = getCallbacks(rootClass);
            Class<?>[] types = new Class<?>[callbacks.length];
            for (int x = 0; x < types.length; x++) {types[x] = callbacks[x].getClass();}
            enhancer.setCallbackFilter(new ProxyCallbackFilter(this.advised.getConfigurationOnlyCopy(), this.fixedInterceptorMap, this.fixedInterceptorOffset));
            enhancer.setCallbackTypes(types);

            // 生成代理类和实例
            return createProxyClassAndInstance(enhancer, callbacks);
        }
    }

大略流程就是这样了。总结一下,就是依据咱们的指标类,生成 jdk 动静代理或者 cglib 代理,前面执行到这个指标类(例子中是 TestController) 的时候,就用生成的代理类去执行,而代理类外面有增强器,也就是咱们的横切面。

下一节讲 cglib 和 jdk 动静代理的工作流程。哈~

退出移动版