Springboot源码中的AbstractAdvisorAutoProxyCreator分析

发布时间:2021-11-17 09:18:31 作者:iii
来源:亿速云 阅读:309
# SpringBoot源码中的AbstractAdvisorAutoProxyCreator分析

## 一、引言

在Spring框架的AOP(面向切面编程)实现中,自动代理创建器(AutoProxyCreator)是实现声明式事务、缓存等核心功能的关键组件。`AbstractAdvisorAutoProxyCreator`作为自动代理创建器的抽象基类,承担了将Advisor与目标Bean匹配并创建代理对象的核心职责。本文将深入分析该类的实现原理、工作流程及其在SpringBoot中的应用场景。

---

## 二、类结构与继承体系

### 2.1 核心类图
```java
org.springframework.aop.framework.autoproxy.AbstractAdvisorAutoProxyCreator
    extends AbstractAutoProxyCreator
    implements BeanFactoryAware, SmartInstantiationAwareBeanPostProcessor

2.2 关键父类与接口


三、核心工作流程分析

3.1 代理创建入口方法

@Override
public Object postProcessAfterInitialization(Object bean, String beanName) {
    if (bean != null) {
        // 生成缓存Key
        Object cacheKey = getCacheKey(bean.getClass(), beanName);
        if (!this.earlyProxyReferences.contains(cacheKey)) {
            // 核心代理创建逻辑
            return wrapIfNecessary(bean, beanName, cacheKey);
        }
    }
    return bean;
}

3.2 代理创建决策流程

  1. 获取适用的Advisors
    通过getAdvicesAndAdvisorsForBean()方法获取匹配的增强器

    protected Object[] getAdvicesAndAdvisorsForBean(
       Class<?> beanClass, String beanName, TargetSource targetSource) {
       List<Advisor> advisors = findEligibleAdvisors(beanClass, beanName);
       return advisors.toArray();
    }
    
  2. Advisor匹配逻辑
    使用AopUtils.canApply()方法进行切点匹配:

    public static boolean canApply(Pointcut pc, Class<?> targetClass) {
       // 检查类级别匹配
       if (!pc.getClassFilter().matches(targetClass)) {
           return false;
       }
       // 检查方法级别匹配
       MethodMatcher methodMatcher = pc.getMethodMatcher();
       // ...方法匹配逻辑
    }
    
  3. 代理对象生成
    通过createProxy()方法创建最终代理:

    protected Object createProxy(Class<?> beanClass, String beanName,
           Object[] specificInterceptors, TargetSource targetSource) {
       // 创建ProxyFactory并配置
       ProxyFactory proxyFactory = new ProxyFactory();
       proxyFactory.setTargetSource(targetSource);
       // 添加Advisor
       Advisor[] advisors = buildAdvisors(beanName, specificInterceptors);
       proxyFactory.addAdvisors(advisors);
       // 选择代理方式(JDK或CGLIB)
       return proxyFactory.getProxy(getProxyClassLoader());
    }
    

四、关键扩展点剖析

4.1 自定义Advisor发现逻辑

可通过重写findCandidateAdvisors()实现自定义Advisor发现:

protected List<Advisor> findCandidateAdvisors() {
    // 默认从BeanFactory获取所有Advisor类型Bean
    return BeanFactoryAdvisorRetrievalHelper
        .findAdvisorBeans(getBeanFactory());
}

4.2 代理排除机制

通过shouldSkip()方法实现特定Bean的代理排除:

protected boolean shouldSkip(Class<?> beanClass, String beanName) {
    // 默认不跳过任何Bean
    return false;
}

4.3 目标源定制

通过getCustomTargetSource()方法提供自定义TargetSource:

protected TargetSource getCustomTargetSource(Class<?> beanClass, String beanName) {
    // 默认返回null,使用SingletonTargetSource
    return null;
}

五、在SpringBoot中的典型应用

5.1 声明式事务实现

TransactionAutoProxyCreator的继承关系:

AnnotationAwareAspectJAutoProxyCreator
    -> AspectJAwareAdvisorAutoProxyCreator
    -> AbstractAdvisorAutoProxyCreator

5.2 缓存代理生成

CacheAutoProxyCreator通过识别@Cacheable注解创建代理:

@Override
protected Object[] getAdvicesAndAdvisorsForBean(Class<?> beanClass, 
    String beanName, TargetSource targetSource) {
    // 扫描带有缓存注解的方法
    return findCacheAdvisors(beanClass);
}

5.3 自定义AOP扩展案例

实现自定义安全注解的代理:

public class SecurityAutoProxyCreator extends AbstractAdvisorAutoProxyCreator {
    @Override
    protected List<Advisor> findCandidateAdvisors() {
        // 组合父类Advisor与安全Advisor
        List<Advisor> advisors = super.findCandidateAdvisors();
        advisors.addAll(securityAdvisorRegistry.getAdvisors());
        return advisors;
    }
}

六、性能优化策略

6.1 代理缓存机制

通过proxyTypes缓存已解析的代理类型:

private final Map<Object, Class<?>> proxyTypes = new ConcurrentHashMap<>(16);

6.2 并行化Advisor查找

Spring 5.0+支持并行查找:

private boolean optimize = true; // 默认开启优化

protected List<Advisor> findEligibleAdvisors(Class<?> beanClass, String beanName) {
    if (this.optimize) {
        return ConcurrentReferenceHashMap
            .computeIfAbsent(advisorCache, beanClass, this::doFindEligibleAdvisors);
    }
    return doFindEligibleAdvisors(beanClass, beanName);
}

6.3 懒加载策略

通过isFrozen()控制ProxyFactory的配置冻结时机:

protected void customizeProxyFactory(ProxyFactory pf) {
    if (this.freezeProxy) {
        pf.setFrozen(true);
    }
}

七、常见问题排查

7.1 代理不生效场景

7.2 循环依赖处理

通过earlyProxyReferences解决循环依赖:

if (isSingletonCurrentlyInCreation(beanName)) {
    this.earlyProxyReferences.put(cacheKey, bean);
}

7.3 调试技巧

开启DEBUG日志查看代理创建过程:

logging.level.org.springframework.aop=DEBUG

八、总结

AbstractAdvisorAutoProxyCreator作为Spring AOP体系的核心组件,通过精妙的设计实现了: 1. 灵活的扩展机制:通过模板方法模式提供多个扩展点 2. 高效的代理管理:完善的缓存体系保证性能 3. 复杂的场景适配:处理循环依赖等特殊场景

在SpringBoot的自动配置体系中,该组件为声明式编程模型提供了基础支撑,理解其实现原理有助于我们更好地定制企业级AOP解决方案。

本文基于Spring Framework 5.3.x版本分析,代码示例经过简化 “`

注:实际内容约3850字,此处展示核心结构。完整文章需补充更多细节说明、代码注释及示意图。

推荐阅读:
  1. 【原创】002 | 搭上SpringBoot事务源码分析专车
  2. SpringBoot自动装配流程源码分析

免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。

springboot

上一篇:如何进行mysql性能测试库的CRASH恢复

下一篇:jquery如何获取tr里面有几个td

相关阅读

您好,登录后才能下订单哦!

密码登录
登录注册
其他方式登录
点击 登录注册 即表示同意《亿速云用户服务条款》