spring 应用启动过程

一般我们在创建springboot应用时,会创建一个启动类,启动类里执行一个main方法:

@SpringBootApplication
public class ExampleApplication {

public static void main(String[] args) {
SpringApplication.run(ExampleApplication.class, args);
}
}
从SpringApplication中可以看到整个启动过程
  1. 创建启动上下文
    DefaultBootstrapContext bootstrapContext = createBootstrapContext();
    微服务从配置中心拉取配置就是在这一阶段操作的

  2. 准备环境
    ConfigurableEnvironment environment = prepareEnvironment(listeners, bootstrapContext, applicationArguments);
    广播ApplicationEnvironmentPreparedEvent事件

  3. 创建banner
    Banner printedBanner = printBanner(environment);

  4. 创建应用程序上下文
    context = createApplicationContext();

  5. 准备应用上下文
    prepareContext(bootstrapContext, context, environment, listeners, applicationArguments, printedBanner);
    广播ApplicationPreparedEvent事件

  6. 刷新上下文
    refreshContext(context);
    这里首先注册了hook,当系统关闭时会走关闭流程:
    if (this.registerShutdownHook) {
    shutdownHook.registerApplicationContext(context);
    }
    执行applicationContext.refresh(),大部分启动操作都是在这里执行,
    这里的finishRefresh阶段会执行Lifecycle,再触发ContextRefreshedEvent

  7. 刷新上下文之后
    afterRefresh(context, applicationArguments);
    这个方法是空的?

  8. listeners.started
    触发ApplicationStartedEvent事件

  9. callRunners
    执行ApplicationRunner和CommandLineRunner,先执行前者

  10. listeners.ready
    触发事件:ApplicationReadyEvent
系统关闭的过程:
上面第6步注册了hook之后,如果系统关闭,会调用ConfigurableApplicationContext的close方法:
if (!context.isActive()) {
return;
}
context.close();
try {
int waited = 0;
while (context.isActive()) {
if (waited > TIMEOUT) {
throw new TimeoutException();
}
Thread.sleep(SLEEP);
waited += SLEEP;
}
}
close方法中,
1. 触发ContextClosedEvent事件
2. 执行Lifecycle的stop方法
3. 执行DisposableBean的destroy方法
4. 执行onClose方法,这个方法貌似又是空的?