目录
  • 前言
  • 正文
    • 注册AutowiredProcessor的BeanDefinition
    • 实例化AutowiredProcessor
    • 创建bean时进行注入
  • 后记

    前言

    @Component
    public class SimpleBean3 {
        @Autowired
        private SimpleBean simpleBean;
    }
    

    @Autowired修饰的字段会被容器自动注入.那么Spring Boot中使如何实现这一功能呢? AutowiredAnnotationBeanPostProcessor!

    BeanPostProcessor implementation that autowires annotated fields, setter methods, and arbitrary config methods. Such members to be injected are detected through annotations: by default, Spring's @Autowired and @Value annotations.
    Also supports JSR-330's @Inject annotation, if available, as a direct alternative to Spring's own @Autowired.

    AutowiredAnnotationBeanPostProcessor(以下简称AutowiredProcessor)间接实现了InstantiationAwareBeanPostProcessor接口.通过postProcessProperties(…)完成@Autowired的注入,本文将按照下图流程梳理AutowiredProcessor的生效逻辑.

    SpringBoot中@Autowired生效方式详解

    SpringBoot-autowired.png

    正文

    注册AutowiredProcessor的BeanDefinition

    SpringApplication#createApplicationContext默认会创建 AnnotationConfigApplicationContext,而AnnotationConfigApplicationContext又会创建AnnotatedBeanDefinitionReader

        public AnnotationConfigApplicationContext() {
            this.reader = new AnnotatedBeanDefinitionReader(this);
            this.scanner = new ClassPathBeanDefinitionScanner(this);
        }
    

    AnnotatedBeanDefinitionReader构造时会调用AnnotationConfigUtils.registerAnnotationConfigProcessors(this.registry),将AutowiredProcessor的BeanDefinition注册到容器

        public static Set<BeanDefinitionHolder> registerAnnotationConfigProcessors(
                BeanDefinitionRegistry registry, @Nullable Object source) {
            //忽略部分代码...
            if (!registry.containsBeanDefinition(AUTOWIRED_ANNOTATION_PROCESSOR_BEAN_NAME)) {
                RootBeanDefinition def = new RootBeanDefinition(AutowiredAnnotationBeanPostProcessor.class);
                def.setSource(source);
                beanDefs.add(registerPostProcessor(registry, def, AUTOWIRED_ANNOTATION_PROCESSOR_BEAN_NAME));
            }
            //忽略部分代码...
            return beanDefs;
        }

    实例化AutowiredProcessor

    在AbstractApplicationContext的refresh阶段,会注册并实例化所有的BeanPostProcessor

    public void refresh() throws BeansException, IllegalStateException {
                //...忽略部分代码
                    // Allows post-processing of the bean factory in context subclasses.
                    postProcessBeanFactory(beanFactory);
                    // Invoke factory processors registered as beans in the context.
                    invokeBeanFactoryPostProcessors(beanFactory);
                    // ########### 这里注册所有的BeanPostProcessor ##########  
                    // Register bean processors that intercept bean creation.
                    registerBeanPostProcessors(beanFactory);
                    // Initialize message source for this context.
                    initMessageSource();
                    // Initialize event multicaster for this context.
                    initApplicationEventMulticaster();
                    // Initialize other special beans in specific context subclasses.
                    onRefresh();
                    // Check for listener beans and register them.
                    registerListeners();
                    // Instantiate all remaining (non-lazy-init) singletons.
                    finishBeanFactoryInitialization(beanFactory);
                    // Last step: publish corresponding event.
                    finishRefresh()
                //...忽略部分代码
        }
    

    实际的注册逻辑交给了PostProcessorRegistrationDelegate

        protected void registerBeanPostProcessors(ConfigurableListableBeanFactory beanFactory) {
            PostProcessorRegistrationDelegate.registerBeanPostProcessors(beanFactory, this);
        }
    

    在PostProcessorRegistrationDelegate中,获取到所有的BeanPostProcessor(基于BeanDefinition),并将其分为几种类型,并按照不同的优先级进行处理化,这块不是这篇文章的重点,我们只需要知道在这里AutowiredProcessor被注册就可以了.

    创建bean时进行注入

    以SimpleBean3的注入为例, 它是单例的,在AbstractApplicationContext.refresh()的finishBeanFactoryInitialization(beanFactory)时创建.

        protected void finishBeanFactoryInitialization(ConfigurableListableBeanFactory beanFactory) {
            //...忽略部分代码
            // Instantiate all remaining (non-lazy-init) singletons.
            beanFactory.preInstantiateSingletons();
        }
    

    调用到了BeanFactory.preInstantiateSingletons(),走到getBean()逻辑

    public void preInstantiateSingletons() throws BeansException {
            //...忽略部分代码
            List<String> beanNames = new ArrayList<>(this.beanDefinitionNames);
            // Trigger initialization of all non-lazy singleton beans...
            for (String beanName : beanNames) {
                RootBeanDefinition bd = getMergedLocalBeanDefinition(beanName);
                if (!bd.isAbstract() && bd.isSingleton() && !bd.isLazyInit()) {
                    if (isFactoryBean(beanName)) {
                        Object bean = getBean(FACTORY_BEAN_PREFIX + beanName);
                        if (bean instanceof FactoryBean) {
                            final FactoryBean<?> factory = (FactoryBean<?>) bean;
                            boolean isEagerInit;
                            if (System.getSecurityManager() != null && factory instanceof SmartFactoryBean) {
                                isEagerInit = AccessController.doPrivileged((PrivilegedAction<Boolean>)
                                                ((SmartFactoryBean<?>) factory)::isEagerInit,
                                        getAccessControlContext());
                            }
                            else {
                                isEagerInit = (factory instanceof SmartFactoryBean &&
                                        ((SmartFactoryBean<?>) factory).isEagerInit());
                            }
                            if (isEagerInit) {
                                getBean(beanName);
                            }
                        }
                    }
                    else {
                        getBean(beanName);
                    }
                }
            }
            //...忽略部分代码
        }

    经过一连串的辗转,最终调用到AbstractAutowireCapableBeanFactory#populateBean

    附上调用链路

    SpringBoot中@Autowired生效方式详解

    image.png

    在populateBean中,会将所有的BeanPostProcessor应用在这个bean上,包括AutowiredProcessor

    protected void populateBean(String beanName, RootBeanDefinition mbd, @Nullable BeanWrapper bw) {
            //...忽略部分代码
            PropertyDescriptor[] filteredPds = null;
            if (hasInstAwareBpps) {
                if (pvs == null) {
                    pvs = mbd.getPropertyValues();
                }
                for (BeanPostProcessor bp : getBeanPostProcessors()) {
                    if (bp instanceof InstantiationAwareBeanPostProcessor) {
                        InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
              //###### 调用到postProcessProperties #####
                        PropertyValues pvsToUse = ibp.postProcessProperties(pvs, bw.getWrappedInstance(), beanName);
                        if (pvsToUse == null) {
                            if (filteredPds == null) {
                                filteredPds = filterPropertyDescriptorsForDependencyCheck(bw, mbd.allowCaching);
                            }
                            pvsToUse = ibp.postProcessPropertyValues(pvs, filteredPds, bw.getWrappedInstance(), beanName);
                            if (pvsToUse == null) {
                                return;
                            }
                        }
                        pvs = pvsToUse;
                    }
                }
            }
        //...忽略部分代码
        }
    

    AutowiredProcessor的postProcessProperties()会进行注入操作,这需要找到注入的元数据(InjectionMetadata)

    public PropertyValues postProcessProperties(PropertyValues pvs, Object bean, String beanName) {     
            //### 找到AutowringMetadata #####
            InjectionMetadata metadata = findAutowiringMetadata(beanName, bean.getClass(), pvs);
            try {
          // #### 注入 ###
                metadata.inject(bean, beanName, pvs);
            }
            catch (BeanCreationException ex) {
                throw ex;
            }
            catch (Throwable ex) {
                throw new BeanCreationException(beanName, "Injection of autowired dependencies failed", ex);
            }
            return pvs;
        }
    

    findAutowiringMetadata()又调用到buildAutowiringMetadata(),生成代表可注入元素的InjectMetadata

    private InjectionMetadata buildAutowiringMetadata(final Class<?> clazz) {
            List<InjectionMetadata.InjectedElement> elements = new ArrayList<>();
            Class<?> targetClass = clazz;
            do {
                final List<InjectionMetadata.InjectedElement> currElements = new ArrayList<>();
                ReflectionUtils.doWithLocalFields(targetClass, field -> {
            //###### 找到带有可注入注解的字段
                    AnnotationAttributes ann = findAutowiredAnnotation(field);
                    if (ann != null) {
                        if (Modifier.isStatic(field.getModifiers())) {
                            if (logger.isInfoEnabled()) {
                                logger.info("Autowired annotation is not supported on static fields: " + field);
                            }
                            return;
                        }
                        boolean required = determineRequiredStatus(ann);
                        currElements.add(new AutowiredFieldElement(field, required));
                    }
                });
                //...忽略部分代码
        }

    findAutowiredAnnotation()根据AutowiredProcessor的实例字段autowiredAnnotationTypes,去查看是否匹配,这个字段是在AutowiredProcessor创建时初始化,可以看到支持@Autowired,@Value,@Inject三种类型的注入标识.最终据此完成注入

    public AutowiredAnnotationBeanPostProcessor() {
            this.autowiredAnnotationTypes.add(Autowired.class);
            this.autowiredAnnotationTypes.add(Value.class);
            try {
                this.autowiredAnnotationTypes.add((Class&lt;? extends Annotation&gt;)
                        ClassUtils.forName("javax.inject.Inject", AutowiredAnnotationBeanPostProcessor.class.getClassLoader()));
                logger.trace("JSR-330 'javax.inject.Inject' annotation found and supported for autowiring");
            }
            catch (ClassNotFoundException ex) {
                // JSR-330 API not available - simply skip.
            }
        }
    

    后记

    最后再来梳理一下整个流程.

    首先是AutowiredPorcessor的BeanDefinition的注册

    => 创建ApplicationContext

    ​ => 创建AnnotatedBeanDefinitionReader

    ​ => 注册BeanDefinition registerAnnotationConfigProcessors

    然后是AutowiredProcessor注册为bean

    => registerBeanPostProcessors

    最后是注入

    ​ => 获取bean getBean()

    ​ => 创建bean doCreateBean()

    ​ =>生成bean populateBean()

    ​ => 应用AutowiredProcessor ibp.postProcessProperties()

    ​ => 找到可注入的字段 buildAutowiringMetadata

    ​ => 注入 metadata.inject

    至此,@Autowired生效逻辑梳理完成

    声明:本站所有文章,如无特殊说明或标注,均为本站原创发布。任何个人或组织,在未征得本站同意时,禁止复制、盗用、采集、发布本站内容到任何网站、书籍等各类媒体平台。如若本站内容侵犯了原著者的合法权益,可联系我们进行处理。