當前位置:成語大全網 - 書法字典 - Springboot讀取配置文件的原理

Springboot讀取配置文件的原理

Springboot中讀取配置文件(application.yaml,application.properties)的過程發生在Spring Application # prepare Environment()階段,而prepare環境屬於整個Springboot應用啟動的非常高級的階段,因為環境的準備是後續bean創建的基礎。讓我們來看看啟動代碼。排除秒表代碼,我們可以發現prepareEnvironment發生在SpringApplication#run中,這幾乎是整個應用程序啟動的多步實質性操作的第壹步。

prepareEnvironment中最重要的是通過simpleApplicationEventMulticast事件觸發偵聽器(EventPublishingRunListener)發出application environment prepared development。

SimpleApplicationEventMulticast事件的實現實際上非常簡單。找到相關的偵聽器來偵聽applicationenvironmentprepareddevelopment,然後逐個調用它們的偵聽器# on application event(event)方法,包括處理配置文件的偵聽器。

在Springboot 2.4.0之前,處理配置文件的偵聽器是ConfigFileApplicationListener,而在2.4.0之後,處理配置文件的偵聽器是environment後處理應用程序偵聽器,並且配置文件的加載發生了很大的變化,這可能會導致壹些行為上的變化,這將在下面詳細討論。

在Springboot 2.4.0之後,配置文件的加載順序根據優先級如下(較大的序列號將被較小的序列號覆蓋):

與上個版本相比,整體屬性加載順序沒有調整。只有應用程序屬性(14、15)具有順序調整。具體調整如下:

如果有多個活動配置文件,如【Test,Dev】,那麽後壹個配置文件中的配置將覆蓋前壹個配置文件(Test)中為同時存在於兩個配置文件配置文件中的配置所配置的值。

前面說了這麽多,最後引出Springboot 2.4之後配置文件加載的行為變化。

考慮到這種情況,如果我想在運行Springboot測試時指定特定的配置文件,我可以將@ active profile(“Test“)添加到測試類中。如果我的應用程序存在於ApplicationEnvironmentPrepareDevent的自定義偵聽器中,將根據當前環境設置配置文件,例如env . addactiveprofile(“Dev“)。

目前,將有兩個活動配置文件,因為springboot-test將在調用應用程序#run之前使用DefaultActiveProfilesResolver將@ active profile註釋定義的配置文件(test)添加到活動配置文件中。當測試運行時,env . addactiveprofile(“Dev“)將添加“Dev“作為活動配置文件,當前活動配置文件將為【“test“,“Dev“】。

根據上面的介紹,對應於以下概要文件(Dev)的配置將覆蓋之前的概要文件(Test)。但是,Springboot 2.4.0之前的版本為我們做了調整,因此測試類中@ActiveProfile中定義的配置文件成為最高優先級。

剛才提到在Springboot 2.4.0之前,用於處理配置文件的偵聽器是ConfigFileApplicationListener,而我們

我們來看看ConfigFileApplicationListener的相關代碼。

查看initializeProfiles(),我發現此時已經調整了配置文件的順序,並在末尾添加了activatedViaProperty(Test),因此配置文件的順序變成了【Dev,Test】。

在profiles.poll()中,原始概要文件的順序被顛倒了,變成了【Dev,Test】。在load()方法中,application-Test.yaml中的值最終由於posttest配置文件而生效。

但是,在Springboot2.4.0之後,ConfigFileApplicationListener已被棄用,並被environment後處理應用程序偵聽器所取代。environmentpostprocessorplicationlistener通過調用configdataEnvironmentPostProcessor完成配置加載。

EnvironmentPostProcessorApplicationListener.java

ConfigDataEnvironmentPostProcessor.java

ConfigDataEnvironmentPostProcessor只是如實設置了活動配置文件,而沒有更改配置文件的順序。最後,調用spring.factories中定義的資源加載器類來加載配置文件。

YamlPropertySourceLoader.java

順便說壹下,Springboot為我們提供了壹個很好的yaml文件解析代碼。當您需要解析yaml文件時,您可能希望直接參考Springboot的YamlPropertySourceLoader。

通過這種方式,壹旦應用程序升級到Springboot 2.4.0,相同的測試代碼將使用application-Dev.yaml中配置的值,這將更改測試結果。

如果妳想解決這個問題,根據上面提到的配置文件的優先級順序,妳可以在@SpringbootTest中設置屬性來覆蓋當前配置文件對應的配置作為最終配置。

理解壹個框架並不容易。壹個小的變化可能會導致應用程序行為的改變。只有刨根問底,不斷總結,才是制定者解決壹切問題的不變方法論。