SpringBoot自动装配流程

Posted Redorblack

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了SpringBoot自动装配流程相关的知识,希望对你有一定的参考价值。

SpringBoot重要的几个注解
SpringBootApplication里面包括 EnableAutoConfiguration、SpringBootConfiguration、ComponentScan

EnableAutoConfiguration:启动自动装配
AutoConfigurationPackage
@Import(AutoConfigurationImportSelector.class) 自动装配导入类
ComponentScan:包扫描,默认是启动类当前包

SpringBoot启动 --SpringApplication.run(<当前启动类>,arg)--当前自动类(primarySource)--prepareContext()容器预先初始化工作--load 加载当前启动类
--refreshContext(熟悉的refresh方法,Spring容器创建以及初始化相关操作)-- invokeBeanFactoryPostProcessors(beanFactory);
执行BeanFactoryPostProcessors方法
执行
invokeBeanFactoryPostProcessors中重要一步 BeanDefinitionRegistryPostProcessor bean定义信息处理器 实现类
ConfigurationClassPostProcessor(重要)实现了 postProcessBeanDefinitionRegistry
processConfigBeanDefinitions 配置Bean的定义信息
doProcessConfigurationClass 解析Configuration注解

processImports(configClass, sourceClass, getImports(sourceClass), true);
// 递归的解析配置类的注解 包含import
private void collectImports(SourceClass sourceClass, Set<SourceClass> imports, Set<SourceClass> visited)
            throws IOException {

        if (visited.add(sourceClass)) {
            for (SourceClass annotation : sourceClass.getAnnotations()) {
                String annName = annotation.getMetadata().getClassName();
                if (!annName.equals(Import.class.getName())) {
                    collectImports(annotation, imports, visited);
                }
            }
            imports.addAll(sourceClass.getAnnotationAttributes(Import.class.getName(), "value"));
        }
    }
    
///执行
this.deferredImportSelectorHandler.process();
    
    public void process() {
            List<DeferredImportSelectorHolder> deferredImports = this.deferredImportSelectors;
            this.deferredImportSelectors = null;
            try {
                if (deferredImports != null) {
                    DeferredImportSelectorGroupingHandler handler = new DeferredImportSelectorGroupingHandler();
                    deferredImports.sort(DEFERRED_IMPORT_COMPARATOR);
                    deferredImports.forEach(handler::register);
                    //开始执行Import注解
                    handler.processGroupImports();
                }
            }
            finally {
                this.deferredImportSelectors = new ArrayList<>();
            }
        }

    }
//执行方法    
public void processGroupImports() {
            for (DeferredImportSelectorGrouping grouping : this.groupings.values()) {      //这步
                grouping.getImports().forEach(entry -> {
                    ConfigurationClass configurationClass = this.configurationClasses.get(
                            entry.getMetadata());
                    try {
                        processImports(configurationClass, asSourceClass(configurationClass),
                                asSourceClasses(entry.getImportClassName()), false);
                    }
                    catch (BeanDefinitionStoreException ex) {
                        throw ex;
                    }
                    catch (Throwable ex) {
                        throw new BeanDefinitionStoreException(
                                "Failed to process import candidates for configuration class [" +
                                        configurationClass.getMetadata().getClassName() + "]", ex);
                    }
                });
            }
        }
//下一步
public Iterable<Group.Entry> getImports() {
            for (DeferredImportSelectorHolder deferredImport : this.deferredImports) {
//实现类     AutoConfigurationImportSelector            this.group.process(deferredImport.getConfigurationClass().getMetadata(),
                        deferredImport.getImportSelector());
            }
            return this.group.selectImports();
        }            

//AutoConfigurationImportSelector 实现类
@Override
        public void process(AnnotationMetadata annotationMetadata, DeferredImportSelector deferredImportSelector) {
            Assert.state(deferredImportSelector instanceof AutoConfigurationImportSelector,
                    () -> String.format("Only %s implementations are supported, got %s",
                            AutoConfigurationImportSelector.class.getSimpleName(),
                            deferredImportSelector.getClass().getName()));
            AutoConfigurationEntry autoConfigurationEntry = ((AutoConfigurationImportSelector) deferredImportSelector)
//获取         AutoConfigurationEntry            .getAutoConfigurationEntry(getAutoConfigurationMetadata(), annotationMetadata);
            this.autoConfigurationEntries.add(autoConfigurationEntry);
            for (String importClassName : autoConfigurationEntry.getConfigurations()) {
                this.entries.putIfAbsent(importClassName, annotationMetadata);
            }
        }
//下一步 这步就开始清晰了
    protected AutoConfigurationEntry getAutoConfigurationEntry(AutoConfigurationMetadata autoConfigurationMetadata,
            AnnotationMetadata annotationMetadata) {
        if (!isEnabled(annotationMetadata)) {
            return EMPTY_ENTRY;
        }
        AnnotationAttributes attributes = getAttributes(annotationMetadata);
        //自动装配开始
        List<String> configurations = getCandidateConfigurations(annotationMetadata, attributes);
        configurations = removeDuplicates(configurations);
        Set<String> exclusions = getExclusions(annotationMetadata, attributes);
        checkExcludedClasses(configurations, exclusions);
        configurations.removeAll(exclusions);
        configurations = filter(configurations, autoConfigurationMetadata);
        fireAutoConfigurationImportEvents(configurations, exclusions);
        return new AutoConfigurationEntry(configurations, exclusions);
    }        
// getCandidateConfigurations方法
protected List<String> getCandidateConfigurations(AnnotationMetadata metadata, AnnotationAttributes attributes) {
        List<String> configurations = 
//getSpringFactoriesLoaderFactoryClass 就是获取 EnableAutoConfiguration.class这个自动装配类
//SpringFactoriesLoader    加载默认目录 META-INF/spring.factories 下面 加载自动装配EnableAutoConfiguration 这种类型的bean 此时加载的只是作为bean的定义信息    SpringFactoriesLoader.loadFactoryNames(getSpringFactoriesLoaderFactoryClass(),
                getBeanClassLoader());
        Assert.notEmpty(configurations, "No auto configuration classes found in META-INF/spring.factories. If you "
                + "are using a custom packaging, make sure that file is correct.");
        return configurations;
    }

加载bean的定义信息到beanfactory 
接下来就是 Beanfactory 执行bean的生命周期流程    
                
                                

总结:SpringBoot启动 SpringApplication.run方法传入当前启动类primarySources
加载当前配置类 在refreshContext中invokeBeanFactoryPostProcessors 执行BeanFactoryPostProcessors(ConfigurationClassPostProcessor) 加载那些自动配置的bean的定义信息、加载完成 执行后续的beanfactory创建bean的流程

以上是关于SpringBoot自动装配流程的主要内容,如果未能解决你的问题,请参考以下文章

SpringBoot启动流程分析:SpringBoot自动装配原理实现

SpringBoot系列之启动流程3-自动装配与@SpringBootApplication注解

SpringBoot - 自动装配 源码解析

SpringBoot - 自动装配 源码解析

springboot自动装配---实现一个自定义自动装配组件

EurekaServer自动装配及启动流程解析