在Spring Boot啟動時執行定製的程式碼
Spring Boot會自動為我們做很多配置,但遲早你需要做一些自定義工作。在本文中,您將學習如何掛鉤應用程式載入程式生命週期並在Spring Boot啟動時執行程式碼 。
1.執行bean初始化的方法
Spring啟動應用程式後執行某些邏輯的最簡單方法是將程式碼作為所選bean引導過程的一部分來執行。
只需建立一個類,將其標記為Spring元件,並將應用程式初始化程式碼放在帶有@PostConstruct 註釋的方法中。理論上,您可以使用建構函式而不是單獨的方法,但將物件的構造與其實際責任分開是一種很好的做法。
@Component class AppInitializator { private static final Logger log = LoggerFactory.getLogger(AppInitializator.class); @PostConstruct private void init() { log.info("AppInitializator initialization logic ..."); // ... } }
還可以在主Spring Boot應用程式類中建立一個帶有@PostConstruct 註釋的方法。不要忘記主類也是框架管理的元件。
@SpringBootApplication public class InitDemoApplication { // ... @PostConstruct private void init() { log.info("InitDemoApplication initialization logic ..."); // ... } }
但這種解決方案感覺就像是一種解決方法而不是真正的解決方案 您可以以非常有限的方式控制Spring框架建立應用程式bean的順序。如果我們想在建立所有bean之前或甚至在框架啟動之前執行初始化邏輯,我們需要找到更好的東西。
2. Spring Boot啟動掛鉤
使用Spring Boot建立的應用程式的美妙之處在於,執行它們所需的唯一內容是Java Runtime Environment和命令列介面。無需外部工具或應用程式。它就像常規的Java SE程式一樣執行。
作為每個Java程式,您都可以在入口應用程式類的靜態main方法中開始執行此類應用程式。這就是你可以掛鉤Spring Boot初始化過程的重點。
首先更改main方法中的程式碼,以將啟動掛鉤附加到單獨的方法中。您應該在應用程式啟動之前新增Spring Boot掛鉤。
public static void main(String[] args) { SpringApplication application = new SpringApplication(InitDemoApplication.class); addInitHooks(application); application.run(args); } static void addInitHooks(SpringApplication application) { // TBD … }
當Spring Boot應用程式啟動時,它會在引導過程的各個步驟上釋出幾個事件。SpringApplication類的API公開了一個方法,我們可以使用該方法為這些事件新增偵聽器。
這是一個在Spring上下文開始建立bean之前釋出的事件上執行啟動方法的示例:
static void addInitHooks(SpringApplication application) { application.addListeners((ApplicationListener<ApplicationEnvironmentPreparedEvent>) event -> { String version = event.getEnvironment().getProperty("java.runtime.version"); log.info("Running with Java {}", version); }); }
根據ofollow,noindex" target="_blank">事件型別 ,Spring傳遞給偵聽器的物件可以讓您訪問幾個有用的操作。在前面的示例中,我們讀取了一些環境屬性,但如果需要,我們也可以修改它。
以下是按啟動時Spring Boot釋出事件的順序排序的可能事件列表:
- ApplicationStartingEvent
- ApplicationEnvironmentPreparedEvent
- ApplicationContextInitializedEvent
- ApplicationPreparedEvent
- ApplicationStartedEvent
- ApplicationReadyEvent
根據我的經驗,最重要的事件 是ApplicationEnvironmentPreparedEvent 。在Spring Boot啟動的這個時刻,尚未建立bean,但您可以訪問整個應用程式配置。通常,這是執行一些自定義啟動程式碼的最佳時機。
3.在啟動時但沒有執行Tomcat時執行程式碼
儘管Spring Boot設計人員在建立框架時考慮了構建胖JAR,但是一些開發人員仍然將Spring Boot應用程式部署到常規的servlet容器(如Tomcat)。如果是這種情況,那麼前一段中的解決方案將無法發揮作用。除非有增加額外步驟。
如果將應用程式部署為常規WAR檔案 ,則可能已經擁有SpringBootServlerInitializator的自定義實現。您只需稍微擴充套件它並新增初始化掛鉤作為應用程式構建過程的一部分。
您可以輕鬆地重用我們在主應用程式類中建立的addInitHooks() 方法。
public class InitDemoWarInitializer extends SpringBootServletInitializer { @Override protected SpringApplicationBuilder configure(SpringApplicationBuilder builder) { InitDemoApplication.addInitHooks(builder.application()); return builder.sources(InitDemoApplication.class); } }
結論
簡而言之,在Spring Boot啟動時執行程式碼有兩個主要選項。最簡單的一個設計用於初始化特定的bean。對於更多全域性案例,該框架有一個專用解決方案,可以使用事件偵聽器掛鉤其生命週期。我們學習瞭如何實現和設定這樣的監聽器。