Spring Boot启动流程源码解析

定义:

BeanFactoryPostProcessor:是一个接口,它允许自定义修改应用程序上下文的beanDefiinition

BeanDefinitionRegistryPostProcessor:是一个接口,继承接口BeanFactoryPostProcessor,该接口新增postProcessBeanDefinitionRegistry方法,方法参数是BeanDefinitionRegistry对象,BeanDefinitionRegistry对象是beanDefiinition的保存中心

BeanPostProcessor:在bean实例化的时候,进行切面处理,在实例化的前执行postProcessBeforeInitialization,在实例化后执行postProcessAfterInitialization 

 

一、SpringApllication实例化,进行初始化操作:

this.resourceLoader = resourceLoader;   // 资源加载器,resourceLoader = null
Assert.notNull(primarySources, "PrimarySources must not be null");  //
this.primarySources = new LinkedHashSet<>(Arrays.asList(primarySources)); //赋值启动类
this.webApplicationType = WebApplicationType.deduceFromClasspath(); //根据classpath存在的类推断web所属应用类型:servelt,Reactive,后面根据不同的类型初始化对应的环境
this.bootstrapRegistryInitializers = getBootstrapRegistryInitializersFromSpringFactories(); //获取启动加载器
setInitializers((Collection) getSpringFactoriesInstances(ApplicationContextInitializer.class)); //设置初始化器
setListeners((Collection) getSpringFactoriesInstances(ApplicationListener.class)); //设置监听器
this.mainApplicationClass = deduceMainApplicationClass(); //根据运行调用栈track,根据main方法找到入口启动类

 

getBootstrapRegistryInitializersFromSpringFactories() :获取启动加载器

它调用getSpringFactoriesInstances(Bootstrapper.class),在多个应用的META-INF/spring.factories文件下获取,key=Bootstrapper的启动类加载器的包路径,并通过class.forName反射,然后把实例放到集合进行Order排序,设置优先级,返回集合。

但是此处,由于META-INF/spring.factories文件没有key=Bootstrapper的信息,故返回了一个空集合。

 

setInitializers(getSpringFactoriesInstances(ApplicationContextInitializer.class))):设置初始化器

getSpringFactoriesInstances(ApplicationContextInitializer.class))的作用:在多个应用的META-INF/spring.factories文件下获取,key=ApplicationContextInitializer初始化器的包路径,并通过class.forName反射,然后把实例放到集合进行Order排序,设置优先级,返回集合,并通过setInitializers对本对象属性initializers(初始化器)进行赋值。初始化器,在spring容器刷新之前,进行接口回调initialize方法

返回的初始化器如下:

0 = "org.springframework.boot.context.ConfigurationWarningsApplicationContextInitializer"
    作用:用作报告常见错误配置的警告(通过分析源码实际情况是如果系统配置包扫描(@ComponentScan)到了org或者org.springframework包就会发出警告并停止系统启动)
    
1 = "org.springframework.boot.context.ContextIdApplicationContextInitializer"
    作用:用于获取、设置spring上下文ID
    
2 = "org.springframework.boot.context.config.DelegatingApplicationContextInitializer"
    作用:使用环境属性 context.initializer.classes,指定的初始化器(initializers)进行初始化工作,如果没有指定则什么都不做。 通过它使得我们可以把自定义实现类配置在 application.properties 里成为了可能。
    
3 = "org.springframework.boot.rsocket.context.RSocketPortInfoApplicationContextInitializer"
    作用:为server设置local.rsocket.server.port通讯监听端口
    
4 = "org.springframework.boot.web.context.ServerPortInfoApplicationContextInitializer"
    作用:将内置servlet容器实际使用的监听端口写入到Environment环境属性中。这样属性local.server.port就可以直接通过@Value注入到测试中,或者通过环境属性Environment获取。
    
5 = "org.springframework.boot.autoconfigure.SharedMetadataReaderFactoryContextInitializer"
    作用:创建一个SpringBoot和ConfigurationClassPostProcessor共用的CachingMetadataReaderFactory对象。实现类为:ConcurrentReferenceCachingMetadataReaderFactory
    
6 = "org.springframework.boot.autoconfigure.logging.ConditionEvaluationReportLoggingListener"
    作用:将ConditionEvaluationReport报告写入日志。

 

 

 

setListeners((Collection) getSpringFactoriesInstances(ApplicationListener.class)) :设置监听器

getSpringFactoriesInstances(ApplicationListener.class)的作用:在多个应用的META-INF/spring.factories文件下获取,key=ApplicationListener初始化器的包路径,并通过class.forName反射,然后把实例放到集合进行Order排序,设置优先级,返回集合,并通过setListeners对本对象属性listeners(监听器)进行赋值。

返回的监听器如下:

 0 = "org.springframework.boot.ClearCachesApplicationListener"
     作用:上下文加载完成后,清理缓存,比如,从META-INF/spring.factories获取的信息后,会放到cache,下次直接从cache拿。
     
 1 = "org.springframework.boot.builder.ParentContextCloserApplicationListener"
     作用:监听当双亲应用的上下文关闭,如果双亲应用关闭了,自身也要关闭。从这个类中拿到上下文去刷新监听双亲关闭事件。
     
 2 = "org.springframework.boot.context.FileEncodingApplicationListener"
     作用:文件编码应用监听器。该监听器实质作用是在收到应用环境准备就绪事件时,对配置中关于文件编码的配置作一个校验,判断配置中的文件编码是否和JVM系统的file.encoding一致。无配置或JVM系统的file.encoding无效的情况下,都不会报异常,但是,当JVM中的file.encoding有效,且在配置中包含了spring.mandatory-file-encoding,而二者又不一致时,就会报IllegalStateException异常。
     
 3 = "org.springframework.boot.context.config.AnsiOutputApplicationListener"
     作用:当收到应用环境准备就绪事件时,对Ansi输出的相关状态进行设置,并绑定到应用环境中
     
 4 = "org.springframework.boot.context.config.DelegatingApplicationListener"
     作用:而是在应用环境准备就绪事件发生时,通过环境中的配置的context.listener.classes,指定自定义的监听器,然后创建一个简单事件广播器实例,放到类属性上,同时,把自定义的监听器,绑定到该广播器上。就可以使得我们自定义的监听器发挥作用
     
 5 = "org.springframework.boot.context.logging.LoggingApplicationListener"
     作用:日志配置监听器,如果没配置日志信息,则使用系统默认的配置。
     
 6 = "org.springframework.boot.env.EnvironmentPostProcessorApplicationListener"
     作用:监听环境准备好后,如果配置信息spring.factories指定了“环境后置处理程序”,则运行该后置处理程序。一般用于自定义环境变量或者编写第三方扩展点
     
 7 = "org.springframework.boot.autoconfigure.BackgroundPreinitializer"
     作用:对于一些耗时的任务,使用一个后台线程尽早触发它们开始执行初始化, 这也可以叫做预初始化。
     设置系统属性spring.backgroundpreinitializer.ignore为true可禁用该机制。 禁用时,相应的初始化任务会发生在前台线程。

 

 

 

二、SpringApplication的run方法

StopWatch stopWatch = new StopWatch();
stopWatch.start(); //用于计时
//【1】创建临时上下文,临时存放一些上下文数据,使用完后会colse.
DefaultBootstrapContext bootstrapContext = createBootstrapContext();
//Spring的上下文
ConfigurableApplicationContext context = null;
​
//【2】配置系统属性java.awt.headless,如果系统缺少硬件,就让系统模拟对应硬件数据以供使用
configureHeadlessProperty();
​
//【3】获取应用运行的监听器
SpringApplicationRunListeners listeners = getRunListeners(args);
//启动监听器
listeners.starting(bootstrapContext, this.mainApplicationClass);
​
try {
    //封装形参args
    ApplicationArguments applicationArguments = new DefaultApplicationArguments(args);
    
    //【4】准备容器环境,初始化environment,即应用上下文环境
    ConfigurableEnvironment environment 
        = prepareEnvironment(listeners, bootstrapContext, applicationArguments);
    //根据用户自定义spring.beaninfo.ignore,为容器设置需要忽略加载的bean
    configureIgnoreBeanInfo(environment);
    
    //【5】打印spring的logo
    Banner printedBanner = printBanner(environment);
    
    //【6】创建上下文和容器
    context = createApplicationContext();
    //为上下文设置应用启动时候的记录器,如:启动报错的报告
    context.setApplicationStartup(this.applicationStartup);
    
    //【7】刷新上下文的准备阶段
    prepareContext(bootstrapContext, context, environment,
                   listeners, applicationArguments, printedBanner);
    //【8】刷新上下文
    refreshContext(context);
    
    //【9】刷新上下文后操作,空方法
    afterRefresh(context, applicationArguments);
    //停止计时
    stopWatch.stop();
    //打印日志
    if (this.logStartupInfo) {
        new StartupInfoLogger(this.mainApplicationClass)
            .logStarted(getApplicationLog(), stopWatch);
    }
    //【10】发布“容器加载完成”事件给监听器
    listeners.started(context);
    //【11】调用ApplicationRunner和CommandLineRunner的run方法,实现spring容器启动后需要做的一些东西,比如加载一些业务数据等
    //默认是没有Runner要执行的
    callRunners(context, applicationArguments);
    //发布"应用running"事件
    listeners.running(context);

 

 

 

【1】创建临时上下文

【2】配置系统硬件属性

【3】获取监听器并启动:getRunListeners(args)

在META-INF/spring.factories文件下获取key=SpringApplicationRunListener的类路径获得org.springframework.boot.context.event.EventPublishingRunListener

并通过class.forName反射实例化返回instances,然后通过new SpringApplicationRunListeners( log, instances, applicationStartup),把EventPublishingRunListener封装到SpringApplicationRunListeners的List集合里。

SpringApplicationRunListener负责在SpringBoot启动的不同阶段,使用内部ApplicationEventMulticaster来广播不同的SpringApplicationEven事件,传递给前面的ApplicatioinListener监听器实现类。比如,“刷新上下文准备阶段” 完成了,就向各个SpringApplicationListener监听器发布“刷新上下文准备阶段” 事件,让各个监听器此时执行对应的逻辑。

 

【4】准备容器环境:prepareEnvironment

上下文环境本质上就是环境信息的集合:系统变量、环境变量、JDK环境信息、命令行参数,默认变量,servlet相关配置变量,随机值、JNDI属性值,以及配置文件(比如application.properties)等。

这些环境变量是有优先级的。对这些信息加载进来,封装到environment对象中。

发布事件

具体prepareEnvironment方法:

//创建相应的应用环境
ConfigurableEnvironment environment = getOrCreateEnvironment();
//根据用户配置,配置environment应用环境
configureEnvironment(environment, applicationArguments.getSourceArgs());
ConfigurationPropertySources.attach(environment);
//发布"上下文环境已准备好"事件,其中一个重要的监听器ConfigFileApplicationListener就是加载项目配置文件的
listeners.environmentPrepared(bootstrapContext, environment);
//把PropertySources中默认的属性“defaultProperties”,移动到PropertySources的末尾。
DefaultPropertiesPropertySource.moveToEnd(environment);
​
Assert.state(!environment.containsProperty("spring.main.environment-prefix"),
        "Environment prefix cannot be set via properties.");
​
//将获取到的environment中的spring.main配置绑定到SpringApplication的source中
bindToSpringApplication(environment);
//是否为自定义环境
if (!this.isCustomEnvironment) {
    //把ConfigurableEnvironment根据应用类型转换成对应对应的ApplicationEnviroment
    environment = convertEnvironment(environment);
}
// 解除附加的特定的环境配置(避免冲突)
ConfigurationPropertySources.attach(environment);
return environment;

 

 

创建相应的应用环境:getOrCreateEnvironment

根据webApplicationType实例化不同的环境类:

SERVLET -> new ApplicationServletEnvironment()

REACTIVE -> new ApplicationReactiveWebEnvironment()

other -> new ApplicationEnvironment()

 

配置environment应用环境:configureEnvironment

if (this.addConversionService) {
    environment.setConversionService(new ApplicationConversionService());
}
//将main函数的args封装成SimpleCommandLinePropertySource加入环境中 
configurePropertySources(environment, args);
//激活相应配置文件,比如:设置spring-profiles.active=prod,封装成SimpleCommandLinePropertySource
//在此激活application-prod.properties这个配置文件
configureProfiles(environment, args);

 

 

 

【5】打印spring的logo

 

【6】创建上下文和容器:createApplicationContext()

根据webApplicationType实例化不同的上下文ConfigurableApplicationContext实现类:

SERVLET -> new AnnotationConfigServletWebServerApplicationContext()

REACTIVE -> new AnnotationConfigReactiveWebServerApplicationContext()

other ->new AnnotationConfigApplicationContext()

于此同时,因为这几个实现类,继承了GenericApplicationContext,而GenericApplicationContext的构造函数中会创建beanFactory,故子类实例化,父类GenericApplicationContext也会跟着实例化,beanFactory其实际上就是IOC容器,类型为DefaultListableBeanFactory,即上下文中有了一个IOC容器

public GenericApplicationContext(DefaultListableBeanFactory beanFactory) {
    Assert.notNull(beanFactory, "BeanFactory must not be null");
    this.beanFactory = beanFactory;
}

 

【7】刷新上下文准备阶段prepareContext

  1. 在装载好了各种环境配置后,去刷新上下文里的配置;

  2. 并创建一些bean对象,其中包含启动类的bean对象创建。

//设置上下文环境
context.setEnvironment(environment);
//执行容器后置处理:其实就是为ioc的转化器ApplicationConversionService设值
postProcessApplicationContext(context);
//执行初始化器的initialize方法
applyInitializers(context);
//listeners是SpringApplicationRunListeners,向各个监听器发送"容器已经准备好"的事件,
listeners.contextPrepared(context);
​
//发布“临时上下文关闭事件”,默认没有监听器监听此事件。
bootstrapContext.close(context);
//打印日志信息
if (this.logStartupInfo) {
    logStartupInfo(context.getParent() == null);
    logStartupProfileInfo(context);
}
​
// Add boot specific singleton beans
//向IOC容器中添加args封装成ApplicationArguments的单例
ConfigurableListableBeanFactory beanFactory = context.getBeanFactory();
beanFactory.registerSingleton("springApplicationArguments", applicationArguments);
​
//IOC容器添加打印springBootBanner单例
if (printedBanner != null) {
    beanFactory.registerSingleton("springBootBanner", printedBanner);
}
//设置BeanDefinition是否能被重载(修改),默认设置为false
if (beanFactory instanceof DefaultListableBeanFactory) {
    ((DefaultListableBeanFactory) beanFactory)
            .setAllowBeanDefinitionOverriding(this.allowBeanDefinitionOverriding);
}
//是否懒加载,默认为false
if (this.lazyInitialization) {
    //上下文添加一个处理bean后置处理器
    context.addBeanFactoryPostProcessor(new LazyInitializationBeanFactoryPostProcessor())
}
// Load the sources,实际上获取的只有启动类对象
Set<Object> sources = getAllSources();
Assert.notEmpty(sources, "Sources must not be empty");
​
//加载启动类的beanDefinition,并注入容器中
load(context, sources.toArray(new Object[0]));
//发布“容器已加载完成”事件
listeners.contextLoaded(context);
 

【8】刷新上下文:refreshContext(context)

刷新之前,会在context上下文添加一个ApplicationContextClosedListener监听,就是为了在shutdown的时候,优雅的关闭应用。

刷新的核心代码如下:

//在应用程序启动期间标记步骤,并收集有关执行上下文数据和处理事件
StartupStep contextRefresh = this.applicationStartup.start("spring.context.refresh");
​
// Prepare this context for refreshing
//1.就是对一些属性赋值。
prepareRefresh();
​
// Tell the subclass to refresh the internal bean factory
//2.就是获取beanFactory,即IOC容器,并刷新容器=为容器设置id
ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory();
​
// Prepare the bean factory for use in this context
//3.容器初始化属性
prepareBeanFactory(beanFactory);
​
// Allows post-processing of the bean factory in context subclasses.
//4.设置beanDefinition的后置处理器、beanFactory的一些属性
postProcessBeanFactory(beanFactory);
​
//在应用程序启动期间标记步骤,并收集有关执行上下文数据和处理事件
StartupStep beanPostProcess = .
    this.applicationStartup.start("spring.context.beans.post-process");
​
// Invoke factory processors registered as beans in the context.
//5.调用容器中的工厂
invokeBeanFactoryPostProcessors(beanFactory);
​
// Register bean processors that intercept bean creation.
//6.注册所有bean的后置处理器
registerBeanPostProcessors(beanFactory);
beanPostProcess.end(); //空方法
// Initialize message source for this context.
// 7.初始化此上下文的消息源,比如国际化
initMessageSource();
​
// Initialize event multicaster for this context.
//8.初始化应用事件发布器,并存在IOC容器中
initApplicationEventMulticaster();
​
// Initialize other special beans in specific context subclasses.
//9.开始刷新
onRefresh();
​
// Check for listener beans and register them.
//10.注册新的监听器
registerListeners();
​
// Instantiate all remaining (non-lazy-init) singletons.
//11.实例化剩余非懒加载的单例bean
finishBeanFactoryInitialization(beanFactory);
​
// Last step: publish corresponding event.
//12.刷新完成的收尾工作
finishRefresh();
 

1、刷新准备阶段:prepareRefresh

this.startupDate = System.currentTimeMillis(); //记录时间点
this.closed.set(false); //目前容器非close状态
this.active.set(true); //目前容器是活跃的
if (this.logger.isDebugEnabled()) {
    if (this.logger.isTraceEnabled()) {
        this.logger.trace("Refreshing " + this);
    } else {
        this.logger.debug("Refreshing " + this.getDisplayName());
    }
}
this.initPropertySources(); //默认空方法,让AbstractApplicationContext子类重载
this.getEnvironment().validateRequiredProperties(); //校验一些必填配置是否可以被解析
//earlyApplicationListeners、applicationListeners两个监听器相互赋值
if (this.earlyApplicationListeners == null) {
    this.earlyApplicationListeners = new LinkedHashSet<>(this.applicationListeners);
}
else {
    // Reset local application listeners to pre-refresh state.
    this.applicationListeners.clear();
    this.applicationListeners.addAll(this.earlyApplicationListeners);
}
this.earlyApplicationEvents = new LinkedHashSet(); //初始化用于发布事件对象的集合
 

2、刷新并获取容器:obtainFreshBeanFactory

 

3、容器初始化属性:prepareBeanFactory(beanFactory)

beanFactory初始化的值:

1. 设置类加载器 :setBeanClassLoader

2.设置Spel表达式的解析器 :setBeanExpressionResolver

3.添加属性编辑器 :addPropertyEditorRegistrar 添加属性编辑器

4.添加Bean后置处理器:addBeanPostProcessor

5.设置忽略指定类的自动装配功能:ignoreDependencyInterface

6.自动装配是,指定对应接口的注入对象(一个接口可有多个对象):registerResolvableDependency

7.设置单例:registerSingleton

 

4、设置beanDefinition的后置处理器、IOC属性:postProcessBeanFactory

1.设置request、session作用域的注入对象

2.设置自动装配时接口注入指定对象

 

5.调用容器中的beanDefinition后置处理器:invokeBeanFactoryPostProcessors

Set<String> processedBeans = new HashSet<>();
​
if (beanFactory instanceof BeanDefinitionRegistry) {
    BeanDefinitionRegistry registry = (BeanDefinitionRegistry) beanFactory;
    List<BeanFactoryPostProcessor> regularPostProcessors = new ArrayList<>();
    List<BeanDefinitionRegistryPostProcessor> registryProcessors = new ArrayList<>();
    //注册两个beanDefinition后置处理器:CachingMetadataReaderFactoryPostProcessor、ConfigurationWarningsPostProcessor
    for (BeanFactoryPostProcessor postProcessor : beanFactoryPostProcessors) {
        if (postProcessor instanceof BeanDefinitionRegistryPostProcessor) {
            BeanDefinitionRegistryPostProcessor registryProcessor =
                    (BeanDefinitionRegistryPostProcessor) postProcessor;
            //调用的是:CachingMetadataReaderFactoryPostProcessor类的该方法,作用是注册beanDefinition后置处理器
            registryProcessor.postProcessBeanDefinitionRegistry(registry);
            registryProcessors.add(registryProcessor);
        }
        else {
            regularPostProcessors.add(postProcessor);
        }
    }
​
    List<BeanDefinitionRegistryPostProcessor> currentRegistryProcessors = new ArrayList<>();
​
    // First, invoke the BeanDefinitionRegistryPostProcessors that implement PriorityOrdered.
    //获取对应类型的后置处理器key:internalConfigurationAnnotationProcessor
    String[] postProcessorNames =
            beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class, true, false);
    for (String ppName : postProcessorNames) {
        if (beanFactory.isTypeMatch(ppName, PriorityOrdered.class)) {
            //添加ConfigurationClassPostProcessor后置处理器
            currentRegistryProcessors.add(beanFactory.getBean(ppName, BeanDefinitionRegistryPostProcessor.class));
            processedBeans.add(ppName);
        }
    }
    //设置beanDefinition后置处理器得优先级
    sortPostProcessors(currentRegistryProcessors, beanFactory);
    //收集要注册到容器得后置处理器,经过前面可得3个后置处理器。
    registryProcessors.addAll(currentRegistryProcessors);
    //把ConfigurationClassPostProcessor后置处理器bean注册到容器
    //这是自动装配的重点方法!!!
    invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry, beanFactory.getApplicationStartup());
    currentRegistryProcessors.clear();
​
    // 执行到这里,重复上一次得操作
    postProcessorNames = beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class, true, false);
    for (String ppName : postProcessorNames) {
        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, beanFactory.getApplicationStartup());
    currentRegistryProcessors.clear();
    
    //中间都是一些重复类似上面的操作 
    ……
​
// Clear cached merged bean definitions since the post-processors might have
// modified the original metadata, e.g. replacing placeholders in values...
//容器清除beanDefinition缓存,因为beanDefinition后置处理器有可能已经修改了beanDefinition的内容,比如占位符
beanFactory.clearMetadataCache();

 

①检索启动类注解入口,自动装配的关键

invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry, beanFactory.getApplicationStartup());
该方法顾名思义,就是调用Bean定义注册后处理器,形参:

currentRegistryProcessors :BeanDefinition注册后处理器集合,就一个ConfigurationClassPostProcessor类处理器

registry:BeanDefinition的注册中心,本质是就是IOC容器里有该注册中心Map

applicationStartup:记录器,用于记录程序执行

②调用接口实现方法

postProcessor.postProcessBeanDefinitionRegistry(registry);
该处理器为类型ConfigurationClassPostProcessor,是接口BeanDefinitionRegistryPostProcessor的实现类,如实现类:

CachingMetadataReaderFactoryPostProcessor.postProcessBeanDefinitionRegistry:是把beanDefinition注册到容器中;

ConfigurationClassPostProcessor.postProcessBeanDefinitionRegistry:是处理有注解的beanDefinition,该方法实现逻辑:

一、在beanDefinition容器中,通过判断是否包含注解@component,拿到启动类

二、通过ConfigurationClassParser.parser解析

1:先解析到@SpringBootApplication,把启动类的beanDefinition封装成SourceClass,被用来更直接检测包含哪些注解的一个类

2:通过递归处理内部类,把有注解的类记录下来

3:解析标注@PropertySource的类,处理类成员的值

4:解析标注@ComponentScan的类,检测到启动类,在启动类所在包及子包进行扫描,直接或间接标注@component的类,都会被扫描到,并把对应类的beanDefinition注册到容器中,然后递归调用ConfigurationClassParser.parser进行解析。

5:解析标注@Import的类,递归解析自身和父注解的@import,解析到@import.value=ImportBeanDefinitionRegistrar 进行记录;解析到@import.value=ImportSelector进行记录,并通过调用selectImports方法把扫描配置文件META-INF/spring.factories,把里面的类扫描,并检测这类是否有注解,如果有,则也需要递归调用ConfigurationClassParser.parser进行解析

经过这一系列解析,就通过注解拿到了全部需要实例化注入到IOC容器的类

  

6、注册bean的后置处理器:registerBeanPostProcessors

注册方式:PostProcessorRegistrationDelegate.registerBeanPostProcessors(beanFactory, applicationContent);

 

7、初始化此上下文的消息源:initMessageSource

比如:国际化

 

8、初始化应用事件发布器,并存在IOC中:initApplicationEventMulticaster

 

9、开始刷新:onRefresh

1.初始化主题来源ThemeSource

2.构造TomcatServletWebServer,并初始化server的配置,并注入到IOC容器中

 

10、注册监听器:registerListeners

 

11.实例化剩余非懒加载的单例:finishBeanFactoryInitialization

拿到容器中的beanDefinition集合,结合bean后置处理器进行实例化,并注入到IOC容器中

 

12.刷新完成的收尾工作:finishRefresh()

1.设置管理bean生命周期的LifecycleProcessor处理器

2.用LifecycleProcessor开始webServerGracefulShutdown、webServerStartStop两个Group 的生命周期管理

3.发布”容器刷新完成“事件

4.为MBeanServer注册LiveBeansView

 

【9】刷新上下文后操作:afterRefresh,空方法

【10】发布“容器加载完成”事件给监听器:listeners.started

【11】启动Spring的Runner加载容器启动后数据

posted @ 2022-03-24 11:51  無名之徒  阅读(596)  评论(0编辑  收藏  举报