鍍金池/ 教程/ Java/ 了解Spring Boot的自動(dòng)配置
通過JMX監(jiān)控Spring Boot應(yīng)用
Spring Boot:定制PropertyEditors
配置是否初始化Bean的方法
Spring Boot的自動(dòng)配置、Command-line Runner
Spring Boot:定制URL匹配規(guī)則
Spring Boot的自動(dòng)配置、Command-line Runner
利用Mockito模擬DB
Spring Boot應(yīng)用的打包和部署
了解Spring Boot的自動(dòng)配置
Spring Boot應(yīng)用的健康監(jiān)控
了解Spring Boot的自動(dòng)配置
初始化數(shù)據(jù)庫(kù)和導(dǎo)入數(shù)據(jù)
Spring Boot應(yīng)用的健康監(jiān)控
Docker with Spring Boot
RESTful by Spring Boot with MySQL
Spring Boot:定制攔截器
Spring Boot:定制static path mappings
Spring Boot with Mysql
Spring Boot:定制自己的starter
在測(cè)試中使用內(nèi)存數(shù)據(jù)庫(kù)
Restful: Spring Boot with Mongodb
Spring Boot with Redis
Spring Boot:定制HTTP消息轉(zhuǎn)換器
Spring Boot: Data Rest Service
Spring Boot:定制type Formatters
在Spring Boot項(xiàng)目中使用Spock框架
選擇Spring Boot項(xiàng)目的內(nèi)嵌容器
通過EmbeddedServletContainerCustomizer接口調(diào)優(yōu)Tomcat
Spring Boot應(yīng)用的打包和部署
Spring Boot Admin的使用
讓你的Spring Boot工程支持HTTP和HTTPS
Spring Boot:定制servlet filters
Spring Boot:定制URL匹配規(guī)則
Spring Boot應(yīng)用的測(cè)試——Mockito
Spring Boot應(yīng)用的測(cè)試——Mockito
Spring Boot:定制servlet filters
通過@Enable*注解觸發(fā)Spring Boot配置

了解Spring Boot的自動(dòng)配置

Spring Boot的自動(dòng)配置給開發(fā)者帶來了很大的便利,當(dāng)開發(fā)人員在pom文件中添加starter依賴后,maven或者gradle會(huì)自動(dòng)下載很多jar包到classpath中。當(dāng)Spring Boot檢測(cè)到特定類的存在,就會(huì)針對(duì)這個(gè)應(yīng)用做一定的配置,自動(dòng)創(chuàng)建和織入需要的spring bean到程序上下文中。

在之前的文章中,我們只是在pom文件中增加各種starter的依賴,例如:spring-boot-starter-data-jpa, spring-boot-starter-web, spring-boot-starter-data-test等等。接下來將在之前的工程的基礎(chǔ)上,觀察在程序的引導(dǎo)啟動(dòng)過程中,Spring Boot通過自動(dòng)配置機(jī)制幫我們做了哪些工作。

How Do

  • Spring Boot啟動(dòng)時(shí)將自動(dòng)配置的信息通過DEBUG級(jí)別的日志打印到控制臺(tái)??梢酝ㄟ^設(shè)置環(huán)境變量(DEBUG)或者程序?qū)傩裕?-debug)設(shè)置程序的日志輸出級(jí)別。
  • 在項(xiàng)目目錄下運(yùn)行DEBUG=true mvn spring-boot:run啟動(dòng)應(yīng)用程序;
  • 在后臺(tái)可以看到DEBUG級(jí)別的日志輸出,在啟動(dòng)日志的最后,可以看到類似AUTO-CONFIGURATION REPORT的字樣。

http://wiki.jikexueyuan.com/project/spring-boot-cookbook-zh/images/cd.png" alt="Positive matches" />

http://wiki.jikexueyuan.com/project/spring-boot-cookbook-zh/images/7.png" alt="Negative matches" />

分析

可以看到,后臺(tái)輸出的自動(dòng)配置信息特別多,好幾頁(yè)屏幕,沒辦法一一分析,在這里選擇一個(gè)postive match和negative match進(jìn)行分析。

Spring Boot通過配置信息指出:特定配置項(xiàng)被選中的原因、列出匹配到對(duì)應(yīng)類的配置項(xiàng)(positive match)、不包括某個(gè)配置項(xiàng)的原因(negative match)。現(xiàn)在以DataSourceAutoConfiguration舉例說明:

  • @ConditionalOnClass 表示對(duì)應(yīng)的類在classpath目錄下存在時(shí),才會(huì)去解析對(duì)應(yīng)的配置文件,對(duì)于DataSourceAutoConfiguration來說就是指:只有javax.sql.DataSource和org.springframwork.jdbc.datasource.embedded.EmbeddedDatabaseType類都能存在時(shí),就會(huì)配置對(duì)應(yīng)的數(shù)據(jù)庫(kù)資源。
  • @ConditionalOnMisssingClass表示對(duì)應(yīng)的類在classpath目錄下找不到。
  • OnClassCondition用于表示匹配的類型(postive or negative)

OnClassCondition是最普遍的瀏覽探測(cè)條件,除此之外,Spring Boot也使用別的探測(cè)條件,如:OnBeanCondition用于檢測(cè)指定bean實(shí)例存在與否、OnPropertyCondition用于檢查指定屬性是否存在等等。

符合negative match代表一些配置類(xxxConfiguration之類的),它們雖然存在于classpath目錄,但是修飾它們的注解中依賴的其他類不存在。導(dǎo)入如果在pom文件中導(dǎo)入spring-boot-autoconfigure包,則GsonAutoConfiguration就會(huì)出現(xiàn)在classpath目錄下,但是該配置類被@ConditionalOnClass(Gson.class)修飾,而com.google.gson.Gson類不在classpath目錄。

@Configuration
@ConditionalOnClass({Gson.class})
public class GsonAutoConfiguration {
    public GsonAutoConfiguration() {
    }

    @Bean
    @ConditionalOnMissingBean
    public Gson gson() {
        return new Gson();
    }
}

總結(jié)

  • @ConditionalOnClass:該注解的參數(shù)對(duì)應(yīng)的類必須存在,否則不解析該注解修飾的配置類;
  • @ConditionalOnMissingBean:該注解表示,如果存在它修飾的類的bean,則不需要再創(chuàng)建這個(gè)bean;可以給該注解傳入?yún)?shù)例如@ConditionOnMissingBean(name = "example"),這個(gè)表示如果name為“example”的bean存在,這該注解修飾的代碼塊不執(zhí)行。

參考資料

  1. Spring Boot實(shí)戰(zhàn):自動(dòng)配置原理分析