Spring源码解析——IoC部分(二)

        首先我们关注一下Spring IoC容器的主要启动过程:Spring的ContextLoaderListener收到Tomcat容器启动完成的消息,初始化SpringIoC容器,开始执行refresh()。refresh()第2步(其他步骤先省略,下文会细说)会调用XmlBeanDefinitionReader读取Xml方式配置的BeanDefinition并注册,第5步会调用BeanFactory后处理器,例如调用ConfigurationClassPostProcessor这个BeanFactory后处理处理标注有@Configuration类的@Import、@Bean、@ComponentScan,调用MapperScannerConfiguration这个BeanFactory后处理Mybatis配置的Dao类。下面是这个关键过程的时序图:

 

 

1    启动过程

    Spring IoC容器启动过程定义在接口ConfigurableApplicationContext.refresh()中,在AbstractApplicationContext中实现,源码:

public void refresh() throws BeansException, IllegalStateException {
    Object var1 = this.startupShutdownMonitor;
    synchronized(this.startupShutdownMonitor) { //启动前加锁同步
        this.prepareRefresh();  //1.准备启动,准备PropertySource,校验必备配置
        //2.新建BeanFactory并初始化,如果是Xml配置方式,这一步会载入BeanDefinition
        ConfigurableListableBeanFactory beanFactory = this.obtainFreshBeanFactory();  
        //3.设置BeanFactory的ClassLoader,Environment,BeanFactory后处理器
        this.prepareBeanFactory(beanFactory); 
        try {
            //4.属于第3步的补充操作,内部逻辑相似
            this.postProcessBeanFactory(beanFactory);   
            //5.调用【BeanFactory后处理器】,对BeanDefinition进行加工。如果是注解配置,会在这
            //一步载入BeanDefinition,而第2步就不会有载入动作
            this.invokeBeanFactoryPostProcessors(beanFactory); 
            //6.注册【Bean后处理器】,这些后处理器是监听器,它们接收容器事件,监听到容器事件后
            //有2个会在Bean初始化前后自动调用的方法        
            this.registerBeanPostProcessors(beanFactory);
            this.initMessageSource();  //7.初始化MessageSource
            this.initApplicationEventMulticaster();  //8.初始化容器事件广播器
            this.onRefresh(); //9.初始化容器,抽象方法,在子类中实现
            this.registerListeners();  //10.注册监听器
            //11.完成BeanFactory初始化,实例化所有非lazy-init的Bean
            this.finishBeanFactoryInitialization(beanFactory); 
            this.finishRefresh();  //12.完成初始化
        } catch (BeansException var9) {
            if (this.logger.isWarnEnabled()) {
                this.logger.warn("Exception encountered during context initialization - cancelling refresh attempt: " + var9);
            }//捕获到异常
            this.destroyBeans();  //销毁Bean
            this.cancelRefresh(var9);  //取消容器的初始化
            throw var9;  //重新抛出异常
        } finally {
            this.resetCommonCaches();
        }
    }
}

2    解析初始化步骤

    接下来重点分析上面每一步的具体工作,下面贴出来的源码会删去一些对我们理解Ioc容器无关紧要的内容。

2.1  prepareRefresh()

    准备启动,准备启动所需的配置(PropertySource),验证属性是否都存在,设置早期监听器和早期事件收集集合。

protected void prepareRefresh() {
    //【删】设置启动时间戳,关闭状态=false,活动状态=true
    this.initPropertySources();  //初始化所有带占位符配置文件
    this.getEnvironment().validateRequiredProperties();  //验证所有必需属性
    //允许应用启动之前的事件,当multicaster一旦可用的时候立刻响应发布的事件
    if (this.earlyApplicationListeners == null) { 
        //添加早期监听器
        this.earlyApplicationListeners = new LinkedHashSet(this.applicationListeners);
    } else {   
        this.applicationListeners.clear();
        this.applicationListeners.addAll(this.earlyApplicationListeners);
    }
    //创建收集早期事件的集合
    this.earlyApplicationEvents = new LinkedHashSet();
}
2.2 obtainFreshBeanFactory()

    刷新BeanFacotry并返回。refreshBeanFactory包括创建BeanFactory对象(并可能加载类信息)。这一步和2.5有一些关联:在Xml配置方式下,Xml文件以IO流的形式读取,解析出Dom文档,BeanDefinition会通过<bean id=""  class=""...>信息载入,随后进行注册。而如果是Springboot注解方式下,这一步不会有载入动作,会使用ConfigurationClassPostPorcessor扫描ClassPath,然后载入BeanDefinition,注册。

//刷新并获取BeanFactory
protected ConfigurableListableBeanFactory obtainFreshBeanFactory() {
    this.refreshBeanFactory();  //启动BeanFactory ?
    return this.getBeanFactory();  //返回BeanFactory
}
/*
* 初始化ApplicationContext,不同的ApplicationContext有不同实现,下面是①AbstractRefreshable- 
* ApplicationContext的实现,在②GenericApplicationContext中仅仅设置了序列化Id
**/
protected final void refreshBeanFactory() throws BeansException {
    if (this.hasBeanFactory()) {
        this.destroyBeans();
        this.closeBeanFactory();  //BeanFactory存在则关闭
    }
    try {
        DefaultListableBeanFactory beanFactory = this.createBeanFactory();//新建BeanFactory
        beanFactory.setSerializationId(this.getId());
        this.customizeBeanFactory(beanFactory);    //允许修改BeanFactory
        this.loadBeanDefinitions(beanFactory);    //加载BeanDefinition
        Object var2 = this.beanFactoryMonitor;
        synchronized(this.beanFactoryMonitor) {  //加锁,设置BeanFactory
            this.beanFactory = beanFactory;
        }
    } catch (IOException var5) {
        throw new ApplicationContextException("I/O error parsing bean definition source for 。。。 ");
    }
}



/*
* 在 XmlWebApplicationContext中的实现,初始化beanDefinitionReader并加载类信息
*/
protected void loadBeanDefinitions(DefaultListableBeanFactory beanFactory) throws BeansException, IOException {
        //使用XmlBeanDefinitionReader读取Bean信息
        XmlBeanDefinitionReader beanDefinitionReader = new XmlBeanDefinitionReader(beanFactory);
        beanDefinitionReader.setEnvironment(this.getEnvironment());
        beanDefinitionReader.setResourceLoader(this);
        beanDefinitionReader.setEntityResolver(new ResourceEntityResolver(this));
        this.initBeanDefinitionReader(beanDefinitionReader);
        //加载类信息,深入下去
        this.loadBeanDefinitions(beanDefinitionReader);
    }
/**
* XmlWebApplicationContext.loadBeanDefinitions(),循环根据配置文件加载类信息
*/
protected void loadBeanDefinitions(XmlBeanDefinitionReader reader) throws IOException {
        //Locations是classpath*下的配置文件:applicationContext.xml,servlet.xml等
        String[] configLocations = this.getConfigLocations();
        if (configLocations != null) {
            String[] var3 = configLocations;
            int var4 = configLocations.length;

            for(int var5 = 0; var5 < var4; ++var5) {//循环读取配置文件
                String configLocation = var3[var5];
                //加载类信息
                reader.loadBeanDefinitions(configLocation);
            }
        }
    }

/**
* AbstractBeanDefinitionReader.loadBeanDefinitions(),对配置文件进行合理编码后加载类信息,有 删减
*/
public int loadBeanDefinitions(String location, @Nullable Set<Resource> actualResources) throws BeanDefinitionStoreException {
        ResourceLoader resourceLoader = this.getResourceLoader();
        //Resource包含配置文件完整URL路径,如:URL
        //[file:/E:/projects/spring_mybatis/out/artifacts/spring_atis_war_exploded/WEB-
        //INF/classes/applicationContext.xml]
        Resource[] resources = ((ResourcePatternResolver)resourceLoader).getResources(location);
        //加载类信息
        count = this.loadBeanDefinitions(resources);
。。。。
}

/**
* XmlBeanDefinitionReader.loadBeanDefinitions(),encodedResource是编码后的配置文件,有删减

*/
public int loadBeanDefinitions(EncodedResource encodedResource) throws BeanDefinitionStoreException {
    //IO流读取配置文件
    InputStream inputStream = encodedResource.getResource().getInputStream();
    return doLoadBeanDefinitions(inputSource, encodedResource.getResource());

。。。 接下来为了节省篇幅,把重要的/跨多个方法的内容写在一起。。。

    //加载配置文件形成包含节点的xml文档
    Document doc = doLoadDocument(inputSource, resource);
    int count = registerBeanDefinitions(doc, resource);

    BeanDefinitionDocumentReader documentReader = createBeanDefinitionDocumentReader();
    documentReader.registerBeanDefinitions(doc, createReaderContext(resource));
    doRegisterBeanDefinitions(doc.getDocumentElement());
}


最后,我们有必要看一下BeanDefinition的注册(注册的通俗含义就是找个东西把它装起来),看一下注册位置和注册方式:
/**
 * 出自DefaultListableApplicationContext,beanDefinitionMap定义是:
 * private final Map<String, BeanDefinition> beanDefinitionMap = new ConcurrentH-
 * ashMap<>(256);
 */
@Override
public void registerBeanDefinition(String beanName, BeanDefinition beanDefinition)
	throws BeanDefinitionStoreException {
if(.....省略....){
        // 注册位置
	this.beanDefinitionMap.put(beanName, beanDefinition);
	}
	else {
		if (hasBeanCreationStarted()) {

		synchronized (this.beanDefinitionMap) {
                // 注册位置
		this.beanDefinitionMap.put(beanName, beanDefinition);
		List<String> updatedDefinitions = new ArrayList<>(this.beanDefinitionNames.size() + 1);
		updatedDefinitions.addAll(this.beanDefinitionNames);
		updatedDefinitions.add(beanName);
		this.beanDefinitionNames = updatedDefinitions;
		if (this.manualSingletonNames.contains(beanName)) {
		Set<String> updatedSingletons = new LinkedHashSet<>(this.manualSingletonNames);
		updatedSingletons.remove(beanName);
		this.manualSingletonNames = updatedSingletons;
		   }
	     }
	}
	else {
		// 注册位置
		this.beanDefinitionMap.put(beanName, beanDefinition);
		this.beanDefinitionNames.add(beanName);
		this.manualSingletonNames.remove(beanName);
	}
}
2.3  prepareBeanFactory()

    设置BeanFactory的ClassLoader,Environment,Bean后处理器,添加自动注入忽略类等。

protected void prepareBeanFactory(ConfigurableListableBeanFactory beanFactory) {
    beanFactory.setBeanClassLoader(this.getClassLoader());  //设置类装载器
    //表达式解析器
    beanFactory.setBeanExpressionResolver(new StandardBeanExpressionResolver(beanFactory.getBeanClassLoader()));
    //注册属性编辑器
    beanFactory.addPropertyEditorRegistrar(new ResourceEditorRegistrar(this, this.getEnvironment()));
    beanFactory.addBeanPostProcessor(new ApplicationContextAwareProcessor(this));//添加Bean后处理器
    beanFactory.ignoreDependencyInterface(EnvironmentAware.class);  //依赖注入时忽略该类
    beanFactory.ignoreDependencyInterface(EmbeddedValueResolverAware.class);
    beanFactory.ignoreDependencyInterface(ResourceLoaderAware.class);
    beanFactory.ignoreDependencyInterface(ApplicationEventPublisherAware.class);
    beanFactory.ignoreDependencyInterface(MessageSourceAware.class);
    beanFactory.ignoreDependencyInterface(ApplicationContextAware.class);
    beanFactory.registerResolvableDependency(BeanFactory.class, beanFactory);  //依赖注入时注入该对象
    beanFactory.registerResolvableDependency(ResourceLoader.class, this);
    beanFactory.registerResolvableDependency(ApplicationEventPublisher.class, this);
    beanFactory.registerResolvableDependency(ApplicationContext.class, this);
    beanFactory.addBeanPostProcessor(new ApplicationListenerDetector(this));
    if (beanFactory.containsBean("loadTimeWeaver")) { //如果支持AspectJ
        beanFactory.addBeanPostProcessor(new LoadTimeWeaverAwareProcessor(beanFactory)); //注册载入时增强处理器
        beanFactory.setTempClassLoader(new ContextTypeMatchClassLoader(beanFactory.getBeanClassLoader()));
    }
    //创建3个单例配置文件
    if (!beanFactory.containsLocalBean("environment")) {
        beanFactory.registerSingleton("environment", this.getEnvironment());
    }
    if (!beanFactory.containsLocalBean("systemProperties")) {
        beanFactory.registerSingleton("systemProperties", this.getEnvironment().getSystemProperties());
    }
    if (!beanFactory.containsLocalBean("systemEnvironment")) {
        beanFactory.registerSingleton("systemEnvironment", this.getEnvironment().getSystemEnvironment());
    }
}
2.4  postProcessBeanFactory()

    在Xml方式下这是一个空方法。我们看一下另一个实现中GenericWebApplicationContext中实现了什么功能:

protected void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) {
    if (this.servletContext != null) {
        beanFactory.addBeanPostProcessor(new ServletContextAwareProcessor(this.servletContext));
        beanFactory.ignoreDependencyInterface(ServletContextAware.class);
    }
    WebApplicationContextUtils.registerWebApplicationScopes(beanFactory, this.servletContext);
    WebApplicationContextUtils.registerEnvironmentBeans(beanFactory, this.servletContext);
}

        可以看到和2.3 prepareBeanFactory()提供了一样的功能,算是对它的功能进行了补充和定制化。

2.5  invokeBeanFactoryPostProcessors()
        这一步是调用所有【BeanFactory后处理器】。Springboot注解配置情况下,这一步才是载入-解析-注册BeanDefinition的地方,做出这一动作的是ConfigurationClassPostProcessor,它的内部有一个ComponentScanParser对src.java.com.xxx包进行扫描,读取所有类信息形成BeanFefinition(不论这些类有没有任何注解)。另外,这一步还有一个叫做PropertySourcesPlaceholderConfigurer的BeanFactory后处理器,这个处理器初始化一个PropertySourcesPlaceholder-Configurer,它就是加载application.properties的类(加载***.yml配置文件的是YamlPropertiesFactoryBean),PropertySourcesPlaceholderConfigurer会按优先级保存在PropertySourcesPlaceholderConfigurer的MutablePropertySources类型的属性中。

protected void invokeBeanFactoryPostProcessors(ConfigurableListableBeanFactory beanFactory) {
    //重点在这里面,这个方法很长?
    PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors(beanFactory 
    //下面的getBeanFactoryPostProcessors()获取【BeanFactory后处理器】
    ,this.getBeanFactoryPostProcessors());   
 
    if (beanFactory.getTempClassLoader() == null && beanFactory.containsBean("loadTimeWeaver")) {
        beanFactory.addBeanPostProcessor(new LoadTimeWeaverAwareProcessor(beanFactory));
        beanFactory.setTempClassLoader(new ContextTypeMatchClassLoader(beanFactory.getBeanClassLoader()));
    }
}
/**
 * 调用【BeanFactory后处理器】,这种处理器主要是对BeanDefinition进行加工,加工动作在所有bean实
 * 例化之前,保证所有Bean实例化前都可以得到处理。注意把【BeanFactory后处理器】和下一节的【Bean
 * 后处理器】区别开,Bean后处理器类似监听器,在监听到容器事件时发挥作用,而且是在Bean实例化前后
 */
public static void invokeBeanFactoryPostProcessors(ConfigurableListableBeanFactory beanFactory, List<BeanFactoryPostProcessor> beanFactoryPostProcessors) {
    Set<String> processedBeans = new HashSet();
    ArrayList regularPostProcessors;
    ArrayList registryProcessors;
    int var9;
    ArrayList currentRegistryProcessors;
    String[] postProcessorNames;
    if (beanFactory instanceof BeanDefinitionRegistry) {   //大IF开始,如果此BeanFactory属于BeanDefinitionRegistry的实例,则它用于处理BeanDefinition
        BeanDefinitionRegistry registry = (BeanDefinitionRegistry)beanFactory;
        regularPostProcessors = new ArrayList();
        registryProcessors = new ArrayList();
        Iterator var6 = beanFactoryPostProcessors.iterator();

        while(var6.hasNext()) { //循环处理所有BeanFactory后处理器
            BeanFactoryPostProcessor postProcessor = (BeanFactoryPostProcessor)var6.next();
            if (postProcessor instanceof BeanDefinitionRegistryPostProcessor) { 
//如果该后处理器属于BeanDefinitionRegistryPostProcessor的实例
                BeanDefinitionRegistryPostProcessor registryProcessor = (BeanDefinitionRegistryPostProcessor)postProcessor;
                //把该BeanDefinition后处理器注册到BeanFactory
                registryProcessor.postProcessBeanDefinitionRegistry(registry); 
                registryProcessors.add(registryProcessor);//标记该后处理器为已注册后处理器
            } else {
                regularPostProcessors.add(postProcessor);//否则标记为普通后处理器
            }
        }

        currentRegistryProcessors = new ArrayList();
        //1.取出刚才的BeanFactory中已注册的【BeanDefinitionRegistryPostProcessor】型
        //BeanFactory后处理器的名称,本次处理有优先排序标记的后处理器
        postProcessorNames = beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class, true, false);
        String[] var16 = postProcessorNames;
        var9 = postProcessorNames.length;

        int var10;
        String ppName;
        for(var10 = 0; var10 < var9; ++var10) {  //循环处理所有取出的后处理器名称
            ppName = var16[var10];
            if (beanFactory.isTypeMatch(ppName, PriorityOrdered.class)) { //如果该处理器有优先排序标记
                currentRegistryProcessors.add(beanFactory.getBean(ppName, BeanDefinitionRegistryPostProcessor.class)); //标记为当前需处理的后处理器
                processedBeans.add(ppName);  //该后处理器本身标记为已加载的Bean
            }
        }
        sortPostProcessors(currentRegistryProcessors, beanFactory);  //对处理器进行优先级排序
        registryProcessors.addAll(currentRegistryProcessors);
        //在registry(上面的BeanFactory)中调用当前需处理的后处理器
        invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry);
        currentRegistryProcessors.clear();  //调用完成,清空当前需处理的后处理器
        //2.再次取出BeanFactory中已注册的BeanDefinition后处理器的名称,本次处理有排序标记的处理器
        postProcessorNames = beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class, true, false);
        var16 = postProcessorNames;
        var9 = postProcessorNames.length;

        for(var10 = 0; var10 < var9; ++var10) {  //循环处理所有取出的后处理器名称
            ppName = var16[var10];
            //如果该后处理器没有加载过并且有排序标记(优先级低于上面的“PriorityOrdered”)
            if (!processedBeans.contains(ppName) && beanFactory.isTypeMatch(ppName, Ordered.class)) {
                currentRegistryProcessors.add(beanFactory.getBean(ppName, BeanDefinitionRegistryPostProcessor.class));  //标记为当前需处理的后处理器
                processedBeans.add(ppName);
            }
        }
        /**
        *重复以上步骤:优先级排序,依次调用,清空
        **/
        sortPostProcessors(currentRegistryProcessors, beanFactory);
        registryProcessors.addAll(currentRegistryProcessors);
        invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry);
        currentRegistryProcessors.clear();
        boolean reiterate = true;

        while(reiterate) {
            reiterate = false;
        
        //3.调用所有剩下的BeanDefinition后处理器,还是要先优先级排序,防止上述过程中有新的带排
        //序标记的处理器加入
         
            postProcessorNames = beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class, true, false);
            String[] var19 = postProcessorNames;
            var10 = postProcessorNames.length;

            for(int var26 = 0; var26 < var10; ++var26) {
                String ppName = var19[var26];
                if (!processedBeans.contains(ppName)) {
                    currentRegistryProcessors.add(beanFactory.getBean(ppName, BeanDefinitionRegistryPostProcessor.class));
                    processedBeans.add(ppName);
                    reiterate = true; //循环直到没有未执行的后处理器
                }
            }

            sortPostProcessors(currentRegistryProcessors, beanFactory);
            registryProcessors.addAll(currentRegistryProcessors);
            invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry);
            currentRegistryProcessors.clear();
        }
        //依次调用所有已注册BeanDefinition后处理器/常规BeanDefinition后处理器
        invokeBeanFactoryPostProcessors((Collection)registryProcessors, (ConfigurableListableBeanFactory)beanFactory);
        invokeBeanFactoryPostProcessors((Collection)regularPostProcessors, (ConfigurableListableBeanFactory)beanFactory);
    } else { //大IF结束,否则直接调用所有后处理器
        invokeBeanFactoryPostProcessors((Collection)beanFactoryPostProcessors, (ConfigurableListableBeanFactory)beanFactory);
    }
    //4.后面所有代码:取出所有【BeanFactoryPostProcessor】类型后处理器(注意前面是
    //【BeanDefinitionRegistryPostProcessor】类型后处理器),按照上述步骤,先处理有优先排序标
    //记的,再处理有排序标记的,最后是无标记的
    String[] postProcessorNames = beanFactory.getBeanNamesForType(BeanFactoryPostProcessor.class, true, false);
    regularPostProcessors = new ArrayList();
    registryProcessors = new ArrayList();
    currentRegistryProcessors = new ArrayList();
    postProcessorNames = postProcessorNames;
    int var20 = postProcessorNames.length;

    String ppName;
    for(var9 = 0; var9 < var20; ++var9) {
        ppName = postProcessorNames[var9];
        if (!processedBeans.contains(ppName)) {
            if (beanFactory.isTypeMatch(ppName, PriorityOrdered.class)) {
                regularPostProcessors.add(beanFactory.getBean(ppName, BeanFactoryPostProcessor.class));
            } else if (beanFactory.isTypeMatch(ppName, Ordered.class)) {
                registryProcessors.add(ppName);
            } else {
                currentRegistryProcessors.add(ppName);
            }
        }
    }
    sortPostProcessors(regularPostProcessors, beanFactory);
    invokeBeanFactoryPostProcessors((Collection)regularPostProcessors, (ConfigurableListableBeanFactory)beanFactory);
    List<BeanFactoryPostProcessor> orderedPostProcessors = new ArrayList();
    Iterator var21 = registryProcessors.iterator();
    while(var21.hasNext()) {
        String postProcessorName = (String)var21.next();
        orderedPostProcessors.add(beanFactory.getBean(postProcessorName, BeanFactoryPostProcessor.class));
    }
    sortPostProcessors(orderedPostProcessors, beanFactory);
    invokeBeanFactoryPostProcessors((Collection)orderedPostProcessors, (ConfigurableListableBeanFactory)beanFactory);
    List<BeanFactoryPostProcessor> nonOrderedPostProcessors = new ArrayList();
    Iterator var24 = currentRegistryProcessors.iterator();
    while(var24.hasNext()) {
        ppName = (String)var24.next();
        nonOrderedPostProcessors.add(beanFactory.getBean(ppName, BeanFactoryPostProcessor.class));
    }
    invokeBeanFactoryPostProcessors((Collection)nonOrderedPostProcessors, (ConfigurableListableBeanFactory)beanFactory);
    beanFactory.clearMetadataCache();
}

        小结一下:这一步总体是在按照先BeanDefinitionRegistryPostProcessor后BeanFactoryPostProcessor,先高优先级再低优先级的顺序调用后处理器。重点还是在调用后处理器的方法这一步:invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry);  我们看看这一步到底在搞什么名堂。

private static void invokeBeanDefinitionRegistryPostProcessors(Collection<? extends BeanDefinitionRegistryPostProcessor> postProcessors, BeanDefinitionRegistry registry) {
    Iterator var2 = postProcessors.iterator();

    while(var2.hasNext()) {
        BeanDefinitionRegistryPostProcessor postProcessor = (BeanDefinitionRegistryPostProcessor)var2.next();
        //循环所有后处理器,重点在这里?
        postProcessor.postProcessBeanDefinitionRegistry(registry);
    }
}

    略去中间的跳转过程,来到最终的ConfigurationClassPostProcessor.processConfigBeanDefinitions()方法中,比较长,我们耐心看下去:

public void processConfigBeanDefinitions(BeanDefinitionRegistry registry) {
    //待处理类集合,注意里面装的是BeanDefinitionHolder,其中的BeanDefinition是要处理的对象。
    List<BeanDefinitionHolder> configCandidates = new ArrayList();
    //取出registry(也就是BeanFactory)中的所有BeanDefinition名称
    String[] candidateNames = registry.getBeanDefinitionNames();
    String[] var4 = candidateNames;
    int var5 = candidateNames.length;

    for(int var6 = 0; var6 < var5; ++var6) { //循环名称并取出BeanDefinition
        String beanName = var4[var6];
        BeanDefinition beanDef = registry.getBeanDefinition(beanName);
        if (!ConfigurationClassUtils.isFullConfigurationClass(beanDef) && !ConfigurationClassUtils.isLiteConfigurationClass(beanDef)) {
            //如果没有完成配置(FullConfig),加入待处理类列表
         if (ConfigurationClassUtils.checkConfigurationClassCandidate(beanDef, this.metadataReaderFactory)) {
                configCandidates.add(new BeanDefinitionHolder(beanDef, beanName));
            }
        } else if (this.logger.isDebugEnabled()) {
            this.logger.debug("Bean definition has already been processed as a configuration class: " + beanDef);
        }
    }
    if (!configCandidates.isEmpty()) {
        //按@Order注解进行排序
        configCandidates.sort((bd1, bd2) -> {
            int i1 = ConfigurationClassUtils.getOrder(bd1.getBeanDefinition());
            int i2 = ConfigurationClassUtils.getOrder(bd2.getBeanDefinition());
            return Integer.compare(i1, i2);
        });
        SingletonBeanRegistry sbr = null;
        //设置Bean实例名称生成器
        if (registry instanceof SingletonBeanRegistry) {
            sbr = (SingletonBeanRegistry)registry;
            if (!this.localBeanNameGeneratorSet) {
                BeanNameGenerator generator = (BeanNameGenerator)sbr.getSingleton("org.springframework.context.annotation.internalConfigurationBeanNameGenerator");
                if (generator != null) {
                    this.componentScanBeanNameGenerator = generator;
                    this.importBeanNameGenerator = generator;
                }
            }
        }
        //检查环境配置
        if (this.environment == null) {
            this.environment = new StandardEnvironment();
        }
        //主角登场,@Configuration注解解析器
        ConfigurationClassParser parser = new ConfigurationClassParser(this.metadataReaderFactory, this.problemReporter, this.environment, this.resourceLoader, this.componentScanBeanNameGenerator, registry);
        //用Set除重
        Set<BeanDefinitionHolder> candidates = new LinkedHashSet(configCandidates);
        HashSet alreadyParsed = new HashSet(configCandidates.size());

        do {
            //重中之重,解析BeanDefinition,我们接下来进去看一下
            parser.parse(candidates);
            //校验
            parser.validate();
            //ConfigurationClass包含以上两步解析完成的多个Bean的定义信息
            Set<ConfigurationClass> configClasses = new LinkedHashSet(parser.getConfigurationClasses());
            configClasses.removeAll(alreadyParsed);
               //Bean信息读取器,该Rreader可以把ConfigurationClass中的Bean信息读取出来,
               //并注册bean定义到容器              
                if (this.reader == null) {
                this.reader = new ConfigurationClassBeanDefinitionReader(registry, this.sourceExtractor, this.resourceLoader, this.environment, this.importBeanNameGenerator, parser.getImportRegistry());
            }
            //注册
            this.reader.loadBeanDefinitions(configClasses);
            alreadyParsed.addAll(configClasses);  //标记为已处理
            candidates.clear();   //清空待处理
            //如果有新的BeanDefinition信息加入到BeanRegistry
            if (registry.getBeanDefinitionCount() > candidateNames.length) {
                String[] newCandidateNames = registry.getBeanDefinitionNames();
                Set<String> oldCandidateNames = new HashSet(Arrays.asList(candidateNames));
                Set<String> alreadyParsedClasses = new HashSet();
                Iterator var12 = alreadyParsed.iterator();
                
                while(var12.hasNext()) {
                    ConfigurationClass configurationClass = (ConfigurationClass)var12.next();
                    alreadyParsedClasses.add(configurationClass.getMetadata().getClassName());
                }

                String[] var23 = newCandidateNames;
                int var24 = newCandidateNames.length;
                //如果新加入的类没有被处理过,加入待处理类集合
                for(int var14 = 0; var14 < var24; ++var14) {
                    String candidateName = var23[var14];
                    if (!oldCandidateNames.contains(candidateName)) {
                        BeanDefinition bd = registry.getBeanDefinition(candidateName);
                        if (ConfigurationClassUtils.checkConfigurationClassCandidate(bd, this.metadataReaderFactory) && !alreadyParsedClasses.contains(bd.getBeanClassName())) {
                            candidates.add(new BeanDefinitionHolder(bd, candidateName));
                        }
                    }
                }

                candidateNames = newCandidateNames;
            }
        } while(!candidates.isEmpty()); //循环直到没有新的类信息需要处理
        //把ImportRegistry注册为单例模式,用来支持importAware
        if (sbr != null && !sbr.containsSingleton(IMPORT_REGISTRY_BEAN_NAME)) {
            sbr.registerSingleton(IMPORT_REGISTRY_BEAN_NAME, parser.getImportRegistry());
        }
        //清除metadataReaderFactory 缓存
        if (this.metadataReaderFactory instanceof CachingMetadataReaderFactory) {
            ((CachingMetadataReaderFactory)this.metadataReaderFactory).clearCache();
        }

    }
}

小结:这一节的主要内容是,BeanFactory对其中的BeanDefinition后处理器和BeanFactory后处理器两种后处理器进行排序调用,对Bean进行一些处理。我们看过了ConfigurationClassPostProcessor对Spring注解的处理,对这句话也有了更深的认识,“Java注解本身只是一个信息标记,要发挥其作用,必须要有一段对应的处理代码”。

2.6  registerBeanPostProcessors()

     注册Bean后处理器(BeanPostPorcessor),这些后处理器类似监听器,会在收到相应的容器事件时发挥作用,BeanPostPorcessor接口有两个方法:postProcessBeforeInitialization(Object bean,String beanName)和postProcessAfterInitialization(Object bean, String),这两个方法在初始化bean前后执行。这一步有一个叫做ConfigurationPropertiesBindingPostProcessor的后处理器,专门用于@ConfigurationProperties注解,把application.properties中的配置绑定到对应bean的对应属性中。

 

public static void registerBeanPostProcessors(
      ConfigurableListableBeanFactory beanFactory, AbstractApplicationContext applicationContext) {
   //取出所有后处理器名称
   String[] postProcessorNames = beanFactory.getBeanNamesForType(BeanPostProcessor.class, true, false);
   //
   int beanProcessorTargetCount = beanFactory.getBeanPostProcessorCount() + 1 + postProcessorNames.length;
   beanFactory.addBeanPostProcessor(new BeanPostProcessorChecker(beanFactory, beanProcessorTargetCount));

   // 把实现了PriorityOrdered接口的后处理器按优先级区分开
   // 按照常规的(internal)/有排序的/无排序的分开
   List<BeanPostProcessor> priorityOrderedPostProcessors = new ArrayList<>();
   List<BeanPostProcessor> internalPostProcessors = new ArrayList<>();
   List<String> orderedPostProcessorNames = new ArrayList<>();
   List<String> nonOrderedPostProcessorNames = new ArrayList<>();

   // 首先注册实现了PriorityOrdered接口的
   for (String ppName : postProcessorNames) {
      if (beanFactory.isTypeMatch(ppName, PriorityOrdered.class)) {
         BeanPostProcessor pp = beanFactory.getBean(ppName, BeanPostProcessor.class);
         priorityOrderedPostProcessors.add(pp);
         if (pp instanceof MergedBeanDefinitionPostProcessor) {
            internalPostProcessors.add(pp);
         }
      }
      else if (beanFactory.isTypeMatch(ppName, Ordered.class)) {
         orderedPostProcessorNames.add(ppName);
      }
      else {
         nonOrderedPostProcessorNames.add(ppName);
      }
   }
   sortPostProcessors(priorityOrderedPostProcessors, beanFactory);
   registerBeanPostProcessors(beanFactory, priorityOrderedPostProcessors);

   // 然后是实现了Ordered接口的
   List<BeanPostProcessor> orderedPostProcessors = new ArrayList<>();
   for (String ppName : orderedPostProcessorNames) {
      BeanPostProcessor pp = beanFactory.getBean(ppName, BeanPostProcessor.class);
      orderedPostProcessors.add(pp);
      if (pp instanceof MergedBeanDefinitionPostProcessor) {
         internalPostProcessors.add(pp);
      }
   }
   sortPostProcessors(orderedPostProcessors, beanFactory);
   registerBeanPostProcessors(beanFactory, orderedPostProcessors);

   // 接下来是所有无排序的
   List<BeanPostProcessor> nonOrderedPostProcessors = new ArrayList<>();
   for (String ppName : nonOrderedPostProcessorNames) {
      BeanPostProcessor pp = beanFactory.getBean(ppName, BeanPostProcessor.class);
      nonOrderedPostProcessors.add(pp);
      if (pp instanceof MergedBeanDefinitionPostProcessor) {
         internalPostProcessors.add(pp);
      }
   }
   registerBeanPostProcessors(beanFactory, nonOrderedPostProcessors);
   // 最后是常规的
   sortPostProcessors(internalPostProcessors, beanFactory);
   registerBeanPostProcessors(beanFactory, internalPostProcessors);

   //注册ApplicationListenerDetector,用来检查所有的ApplicationListener,它处于处理器链末端。
   beanFactory.addBeanPostProcessor(new ApplicationListenerDetector(applicationContext));
}

 

2.7  initMessageSource

        初始化MessageSource Bean,国际化。

/**
* 初始化消息源
*/
protected void initMessageSource() {
   ConfigurableListableBeanFactory beanFactory = getBeanFactory();
   if (beanFactory.containsLocalBean(MESSAGE_SOURCE_BEAN_NAME)) {
      this.messageSource = beanFactory.getBean(MESSAGE_SOURCE_BEAN_NAME, MessageSource.class);
      // 给MessageSource设置父级MessageSource
      if (this.parent != null && this.messageSource instanceof HierarchicalMessageSource) {
         HierarchicalMessageSource hms = (HierarchicalMessageSource) this.messageSource;
         if (hms.getParentMessageSource() == null) {
            hms.setParentMessageSource(getInternalParentMessageSource());
         }
      }
      if (logger.isTraceEnabled()) {
         logger.trace("Using MessageSource [" + this.messageSource + "]");
      }
   }
   else {
      // 创建一个空的MessageSource
      DelegatingMessageSource dms = new DelegatingMessageSource();
      dms.setParentMessageSource(getInternalParentMessageSource());
      this.messageSource = dms;
      beanFactory.registerSingleton(MESSAGE_SOURCE_BEAN_NAME, this.messageSource);
      if (logger.isTraceEnabled()) {
         logger.trace("No '" + MESSAGE_SOURCE_BEAN_NAME + "' bean, using [" + this.messageSource + "]");
      }
   }
}
2.8  initApplicationEventMulticaster

    初始化容器事件广播电台(内部是一个装有Listener的Set和一个线程池,需要通知时,依次异步通知对监听了这种事件的监听器)。

/**
* 从BeanFactory取出或创建新的广播器并设置到当前ApplicationContext
*/
protected void initApplicationEventMulticaster() {
   ConfigurableListableBeanFactory beanFactory = getBeanFactory();
   //从BeanFactory获取
   if (beanFactory.containsLocalBean(APPLICATION_EVENT_MULTICASTER_BEAN_NAME)) {
      this.applicationEventMulticaster =
            beanFactory.getBean(APPLICATION_EVENT_MULTICASTER_BEAN_NAME, ApplicationEventMulticaster.class);
      if (logger.isTraceEnabled()) {
         logger.trace("");
      }
   }
   else { //没有则新建
      this.applicationEventMulticaster = new SimpleApplicationEventMulticaster(beanFactory);
      beanFactory.registerSingleton(APPLICATION_EVENT_MULTICASTER_BEAN_NAME, this.applicationEventMulticaster);
      if (logger.isTraceEnabled()) {
         logger.trace("");
      }
   }
}
2.9  onRefresh()

        用于创建特殊Bean的模板方法,默认没有任何操作。

2.10  registerListeners()

        注册监听器,发布早期积累的容器事件,ApplicationMutiCaster内部有一个线程池和Set<Listener>,发布事件时会筛选监听了当前事件的监听器,然后调用监听器异步执行。

/**
* 注册实现了ApplicationListener接口的监听器Bean,其他非Bean的监听器也可以注册但不推荐。
*/
protected void reApplicationgisterListeners() {
   // 首先注册BeanFactory中指定的监听器
   for (ApplicationListener<?> listener : getApplicationListeners()) {
      getApplicationEventMulticaster().addApplicationListener(listener);
   }

   // 通过ClassName注册其他监听器,但不要在这里初始化非监听器的类
   String[] listenerBeanNames = getBeanNamesForType(ApplicationListener.class, true, false);
   for (String listenerBeanName : listenerBeanNames) {
      getApplicationEventMulticaster().addApplicationListenerBean(listenerBeanName);
   }

   // 把早期积累的事件广播出去
   Set<ApplicationEvent> earlyEventsToProcess = this.earlyApplicationEvents;
   this.earlyApplicationEvents = null;
   if (earlyEventsToProcess != null) {
      for (ApplicationEvent earlyEvent : earlyEventsToProcess) {
         getApplicationEventMulticaster().multicastEvent(earlyEvent);
      }
   }
}
2.11  finishBeanFactoryInitialization()

        完成容器的初始化,使用BeanDefinition创建所有非懒加载的Bean(懒加载:lazy-init,标注有@Lazy的就是懒加载)。

protected void finishBeanFactoryInitialization(ConfigurableListableBeanFactory beanFactory) {
   // 初始化容器的conversionService.
   if (beanFactory.containsBean(CONVERSION_SERVICE_BEAN_NAME) &&
         beanFactory.isTypeMatch(CONVERSION_SERVICE_BEAN_NAME, ConversionService.class)) {
      beanFactory.setConversionService(
            beanFactory.getBean(CONVERSION_SERVICE_BEAN_NAME, ConversionService.class));
   }

   //给没有Bean后处理器的Bean添加一个默认的内置的占位符处理器,处理@Vaule、@Configuratio- 
   //nProperties和从注解取值
   if (!beanFactory.hasEmbeddedValueResolver()) {
      beanFactory.addEmbeddedValueResolver(strVal -> getEnvironment().resolvePlaceholders(strVal));
   }

   // 实例化运行时增强Bean,使得AOP增强处理器可以更早注册进来.
   String[] weaverAwareNames = beanFactory.getBeanNamesForType(LoadTimeWeaverAware.class, false, false);
   for (String weaverAwareName : weaverAwareNames) {
      getBean(weaverAwareName);
   }

   // 停止使用临时类加载器做类型判断.
   beanFactory.setTempClassLoader(null);

   // 冻结beandefinition信息,防止更改beandefinition.
   beanFactory.freezeConfiguration();

   // 实例化所有非懒加载Bean
   beanFactory.preInstantiateSingletons();
}

2.12  finishRefresh()

        完成容器刷新。

protected void finishRefresh() {
   // 清除容器加载BeanDefinition过程中保存的资源(Resource)
   clearResourceCaches();

   // 初始化生命周期处理器
   initLifecycleProcessor();

   // 刷新生命周期处理器
   getLifecycleProcessor().onRefresh();

   // 发布ContextRefreshedEvent事件
   publishEvent(new ContextRefreshedEvent(this));

   // 注册快照,用于保存Bean和Bean依赖关系的快照
   LiveBeansView.registerApplicationContext(this);
}

        这篇文章解析了Spring容器启动过程,详细叙述了BeanDefinition的载入-解析-注册过程,但IoC的关键动作“依赖注入”还没有涉及,我们在下一篇文章中对源码进行解读。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值