SpringBoot的启动原理
创建启动器
SpringBoot通过调用主程序启动应用环境。下面代码为应用启动器的基本代码。
启动器
1 | // 标注这是SpringBoot应用 |
进入SpringApplication.run
方法之后,发现程序会调用new SpringApplication
来创建应用。
1 | public static ConfigurableApplicationContext run(Class<?>[] primarySources, String[] args){ |
在new SpringApplication
创建实例的过程中,应用容器会从加载一些主类。比如代码中所写的:
初始化SpringApplication
1 | public SpringApplication(ResourceLoader resourceLoader, Class<?>... primarySources) { |
在创建的过程中,在setInitializers
和setListeners
的过程是类似的。主要方法就是从META-INF/spring.factories
中加载特定的key值下的value。
1 | private <T> Collection<T> getSpringFactoriesInstances(Class<T> type, Class<?>[] parameterTypes, Object... args) { |
上面分析了getSpringFactoriesInstances
这个方法是如何获取实例的,其中获取的途径就是使用SpringFactoriesLoader.loadFactoryNames
获取全类名,然后通过反射进行创建实例。
1 | public static List<String> loadFactoryNames(Class<?> factoryClass, @Nullable ClassLoader classLoader) { |
上面的一系列方法只是为给SpringApplication
进行初始化的相关操作,下一步,调用SpringApplication.run
正式运行容器.
启动器启动
在新建完SpringApplication后,使用run方法正式启动容器
1 | new SpringApplication(primarySources).run(args); |
getRunListeners方法与启动Listeners
获得所有的listeners,然后调用 listeners.starting();
运行监听器。
在这个方法中,使用到了getSpringFactoriesInstances
方法,上面说到,这个方法实际上就是从spring.factory
中获取所有的key为特定值的类。在getRunListeners方法里就是获取所有的key为SpringApplicationRunListener
的所有value。参考下图中内容:
1 | private SpringApplicationRunListeners getRunListeners(String[] args) { |
经过上面的步骤,就可以获取到所有的RunListeners。使用starting方法来批量的开启listener。其内部实现如下面的代码。是使用for循环将所有加载到的listeners启动。
1 | public void starting() { |
prepareEnvironment 准备环境
1 | private ConfigurableEnvironment prepareEnvironment(SpringApplicationRunListeners listeners, |
在配置环境的过程中,需要配置properties
属性和profile
。
1 | protected void configureEnvironment(ConfigurableEnvironment environment, String[] args) { |
configureProfiles 配置profile
1 | protected void configureProfiles(ConfigurableEnvironment environment, String[] args) { |
printBanner 打印标志
printBanner方法用来打印运行程序时的标志,见下图
这个方法最后通过print
方法来输出
1 | public Banner print(Environment environment, Class<?> sourceClass, PrintStream out) { |
createApplicationContext 创建应用上下文环境
createApplicationContext
方法用来策略创建指定的applicationContext;
1 | protected ConfigurableApplicationContext createApplicationContext() { |
prepareContext 准备上下文
1 | private void prepareContext(ConfigurableApplicationContext context, ConfigurableEnvironment environment, |
refreshContext 刷新上下文
用于刷新上下文,刷新上下文的过程其实就是IOC容器初始化的过程(扫描、加载、创建所有的组件)。如果是web应用,还会自动启动嵌入式的tomcat.具体方法会单拿出来一篇来分析refresh的过程。
1 |
|
调用callRunners
启动过程图解
使用一张简单的流程图将上面所有的主要方法串联起来,来查看SpringBoot的启动流程。
在整个启动流程的过程中又一个重要的组件就是listeners.它来监听应用运行的过程。在程序中的体现就是特定的节点调用listeners的回调方法。具体的调用listeners过程如下图所展示的:
结束
这篇文章根据代码来分析SpringBoot的启动过程。分析的比较潦草,有些地方分析的不清晰或者分析出错的地方,欢迎指正,共同进步!。