3.1_SpringBoot內部處理機制解析
前言
目前基於SpringBoot進行Web應用開發已經成為一個趨勢,Spring官網內部的很多入門Demo都是基於SpringBoot的,因此掌握SpringBoot成為當下基於Java的Web開發的必備技能。
SpringBoot相對於傳統Servlet容器模式還是有幾點顛覆性的改變的:
1、SpringBoot應用程序使用jar來運行,而傳統模式是打成war包部署到Servlet容器中。使用jar的模式有助於減輕運維人員的工作,更便於在Docker這種雲平臺的運行環境中使用;
2、SpringBoot是應用啟動容器,而傳統模式是容器啟動應用。這樣SpringBoot的一個優勢是程序本身管理了容器版本,業務代碼與運行容器是直接綁定的;
3、SpringBoot使用了大量的AutoConfig來進行探測和應用配置,使得代碼配置很簡單,但內部處理細節也被隱藏的很深。
接下來我們將從一個簡單的基於SpringBoot的Web工程開始,來探究SpringBoot的啟動和加載過程,以便深入理解SpringBoot的內部工作機制。
樣例工程
工程名稱:sample-helloworld
package:com.sample.helloworld
main:SampleApplication
controller:SampleController
pojo:Greeting
pom.xml
parent使用spring-boot-starter-parent,依賴只有spring-boot-starter-web。
spring-boot-starter-parent中定義了項目構建的一些定義,而他的parent——spring-boot-dependencies中定義了SpringBoot可能使用到的所有第三方依賴的版本。
spring-boot-starter-web是一個pom工程,定義了一個web工程的基本依賴。
SampleApplication:直接啟動應用。
SampleController:使用SpringMVC的RestController返回一個JSON對象。
Greeting:定義一個簡單的POJO來作為返回對象。
最終效果是訪問localhost:8080的時候,頁面會展示一個JSON字符串。
啟動代碼解析
啟動代碼只有一行:SpringApplication.run(SampleApplication.class, args);
1、SpringApplication的run方法內部是new了SpringApplication,構造函數中保存了SourceClass,獲取了外部配置的ApplicationContextInitializer和ApplicationListener,來支持外部組件的初始化和事件監聽器。這些外部的功能擴展功能的配置信息都定義在各個jar的/META-INF/spring.factories的配置文件中,Spring通過SpringFactoriesLoader可以加載到這些配置信息。
2、執行SpringApplication實例的run方法。
2.1、創建SpringApplication自己的SpringApplicationRunListener,其實是代理調用了加載進來的ApplicationListener。
2.2、準備Environment,包括解析Properties文件、處理profile等。
2.3、創建ApplicationContext,因為現在應用類型是Servlet,創建的是AnnotationConfigServletWebServerApplicationContext。
2.4、對ApplicationContext進行配置,比如設置BeanNameGenerator、ResourceLoader等。然後加載資源,即解析傳入的SourceClass來獲取Bean定義。
2.5、啟動ApplicationContext,AnnotationConfigServletWebServerApplicationContext繼承了SpringFrameWork本身提供的GenericWebApplicationContext提供的功能並進行了擴展,以支持配置並啟動Embed Tomcat。
2.5.1、對BeanFactory進行一些初始化配置。
2.5.2、執行BeanFactoryPostProcessor,其中包括對BeanDefinition的進一步處理。最重要的是ConfigurationClassPostProcessor,用來解析處理所有@Configuration標簽類,並將Bean定義註冊到BeanFactory中。因為@SpringBootApplication中包含了@EnableAutoConfiguration的meta-annotation,會進行自動配置處理,基本原理是判斷工程依賴了哪些第三方組件並對其進行自動化配置,這樣處理完@Configuration標簽後,BeanFactory中就已經有大量的Bean定義了。
2.5.3、註冊BeanPostProcessor,這些Processor會在首次getBean時執行。主要功能包括進行Autowire、Required等標簽的處理,完成自動綁定等功能。也有特殊的關於WebServleterFactory的後續處理。
2.5.4、在ApplicationContext的onRefresh方法中會對Web容器(Tomcat)進行配置,包括註冊Servlet、Filter、Listener等。
2.5.5、在ApplicationContext的finishRefresh方法中啟動Web容器(Tomcat),完成應用的啟動。
後續將會在3.1.x章節繼續對系統啟動的各個關鍵點進行詳細解析。
3.1_SpringBoot內部處理機制解析