目 录CONTENT

文章目录

SpringBoot启动配置原理(6)

Eric
2022-02-15 / 0 评论 / 0 点赞 / 155 阅读 / 571 字 / 正在检测是否收录...
温馨提示:
本文最后更新于 2023-12-12,若内容或图片失效,请留言反馈。部分素材来自网络,若不小心影响到您的利益,请联系我们删除。

SpringBoot启动配置原理

1 启动流程

  • 创建SpringApplication对象。
public class SpringApplication {
    //SpringBoot应用启动,调用此方法
    public static ConfigurableApplicationContext run(Object source, String... args) {
        return run(new Object[] { source }, args);
    }
      
    public static ConfigurableApplicationContext run(Object[] sources, String[] args) {
        return new SpringApplication(sources).run(args);
    }
    
    public SpringApplication(Object... sources) {
        //初始化
        initialize(sources);
    }
    private void initialize(Object[] sources) {
        //保存主配置类
        if (sources != null && sources.length > 0) {
            this.sources.addAll(Arrays.asList(sources));
        }
        //当前应用是否是web应用
        this.webEnvironment = deduceWebEnvironment();
        //从类路径下找到META-INF/spring.factories配置的所有ApplicationContextInitializer,然后保存起来
        setInitializers((Collection) getSpringFactoriesInstances(
                ApplicationContextInitializer.class));
        //从类路径下找到META-INF/spring.factories配置的所有ApplicationListener,然后保存起来
        setListeners((Collection) getSpringFactoriesInstances(ApplicationListener.class));
        //从多个配置类中找到有main方法的主配置类
        this.mainApplicationClass = deduceMainApplicationClass();
    }
    //其他略
}

ApplicationContextInitializer.png

ApplicationListener.png

  • 通过SpringApplication对象调用run()方法。
public class SpringApplication {
     /**
     * Run the Spring application, creating and refreshing a new
     * {@link ApplicationContext}.
     * @param args the application arguments (usually passed from a Java main method)
     * @return a running {@link ApplicationContext}
     */
    public ConfigurableApplicationContext run(String... args) {
        StopWatch stopWatch = new StopWatch();
        stopWatch.start();
        ConfigurableApplicationContext context = null;
        FailureAnalyzers analyzers = null;
        configureHeadlessProperty();
         //获取SpringApplicationRunListeners,从类路径下的找到META-INF/spring.factories配置的所有SpringApplicationRunListener
        SpringApplicationRunListeners listeners = getRunListeners(args);
        //回调所有SpringApplicationRunListener的starting方法
        listeners.starting();
        try {
             //封装命令行参数
            ApplicationArguments applicationArguments = new DefaultApplicationArguments(
                    args);
             /*
             * 准备环境:
             *  - 创建环境完成后回调所有SpringApplicationRunListener的environmentPrepared方法;表示环境准备完成
             */
            ConfigurableEnvironment environment = prepareEnvironment(listeners,
                    applicationArguments);
             //打印Banner
            Banner printedBanner = printBanner(environment);
             //创建ApplicationContext。决定创建Web的IOC容器还是普通的IOC容器
            context = createApplicationContext();
            analyzers = new FailureAnalyzers(context);
             //准备上下文环境,将environment保存到IOC容器中,applyInitializers(context);回到之前保存的所有的ApplicationContextInitializer的initialize()方法,回调listeners.contextPrepared(context);
            prepareContext(context, environment, listeners, applicationArguments,
                    printedBanner);
            //prepareContext完成后,回调listeners.contextLoaded(context);
             
            //刷新容器。IOC容器初始化
            refreshContext(context);
             //从IOC容器中获取所有的ApplicationRunner和CommandLineRunner进行回调
            afterRefresh(context, applicationArguments);
             //所有的SpringApplicationRunListener回调finished方法
            listeners.finished(context, null);
            stopWatch.stop();
            if (this.logStartupInfo) {
                new StartupInfoLogger(this.mainApplicationClass)
                        .logStarted(getApplicationLog(), stopWatch);
            }
             //整个SpringBoot启动完成以后,返回启动的IOC容器
            return context;
        }
        catch (Throwable ex) {
            handleRunFailure(context, listeners, analyzers, ex);
            throw new IllegalStateException(ex);
        }
    }    
    
}

2 总结事件回调机制

  • 需要配置在META-INF/spring.factories的事件是:

    • ApplicationContextInitializer。
    • ApplicationListener。
  • 不需要配置在META-INF/spring.factories,只需要加入到IOC容器的事件是:

    • ApplicationRunner。
    • CommandLineRunner。
0

评论区