SpringBoot源码分析(二)启动原理
词汇族 人气:0
**Springboot的jar启动方式,是通过IOC容器启动 带动了Web容器的启动**
**而Springboot的war启动方式,是通过Web容器(如Tomcat)的启动 带动了IOC容器相关的启动**
# 一、不可不说的Web容器(如Tomcat)
不管是jar启动还是war包启动,都绕不开web容器相关。先了解这个怎么工作的,以Tomcat为例,
看看Springboot 怎么来自动装配tomcat 相关的组件?
## 1.1 相关类
相关包org.springframework.boot.autoconfigure.web,在springboot的自动配置包的web下(自动配置功能都在这个autoconfigure包下)。
![1585411391302](C:\Users\yejian\AppData\Roaming\Typora\typora-user-images\1585411391302.png)
embedded(内嵌)里面四个类一个A四B,一个:
**EmbeddedWebServerFactoryCustomizerAutoConfiguration(内嵌web容器工厂自定义定制器装配类) **
四个具体容器相关:
JettyWebServerFactoryCustomizer、NettyWebServerFactoryCustomizer、TomcatWebServerFactoryCustomizer、UndertowWebServerFactoryCustomizer
**一个自动配置类+四个常用web容器定制器**
## 1.2.工作流程
以Tomcat定制器切入,断点落在构造器上,启动。
总结出它的工作流程:
1.启动=》2.createWebServer=》
3.拿TomcatServletWebServerFactory(tomcatWeb容器工厂)=》
4.拿WebServerFactoryCustomizer(工厂定制器)
也就是拿工厂定制器获取工厂,再拿工厂获取web容器,这么个流程
## 1.3.具体工作
可以仔细看下相关工厂是如何配置创建容器运行的
TomcatServletWebServerFactory的创建Tomcat方法
```java
public WebServer getWebServer(ServletContextInitializer... initializers) {
Tomcat tomcat = new Tomcat();
File baseDir = (this.baseDirectory != null) ? this.baseDirectory
: createTempDir("tomcat");
tomcat.setBaseDir(baseDir.getAbsolutePath());
Connector connector = new Connector(this.protocol);
tomcat.getService().addConnector(connector);
customizeConnector(connector);
tomcat.setConnector(connector);
tomcat.getHost().setAutoDeploy(false);
configureEngine(tomcat.getEngine());
for (Connector additionalConnector : this.additionalTomcatConnectors) {
tomcat.getService().addConnector(additionalConnector);
}
prepareContext(tomcat.getHost(), initializers);
return getTomcatWebServer(tomcat);
}
```
创建Tocmat类并设置相关这些组件,应该很熟悉(以后出Tomcat源码分析)。
TomcatWebServerFactoryCustomizer的customize定制方法,通过类serverProperties配置文件设置工厂的属性
# 二、SpringBoot的jar启动方式
来自:
```java
public static void main(String[] args) {
SpringApplication.run(StudySpringbootApplication.class, args);
}
```
打开源码:
```java
public static ConfigurableApplicationContext run(Class[] primarySources,
String[] args) {
return new SpringApplication(primarySources).run(args);
}
```
其实两步,一步创建SpringApplication ,一步run运行。
创建类做的事情比较简单,主要包括判断web应用类型、用SpringFactories技术从 spring.factories 文件里获取ApplicationContextInitializer 对应类和ApplicationListener,最后获取当前应用的启动类的类对象。
## 2.1 run方法
```java
public ConfigurableApplicationContext run(String... args) {
//StopWatch是记录时间的工具,为了打印那句SpringBoot启动耗时的
StopWatch stopWatch = new StopWatch();
stopWatch.start();
ConfigurableApplicationContext context = null;
Collection
加载全部内容