spring boot會自動為我們做很多配置,但遲早你需要做一些自定義工作。在本文中,您將學(xué)習(xí)如何掛鉤應(yīng)用程序引導(dǎo)程序生命周期并在spring boot啟動時執(zhí)行代碼。
1.執(zhí)行bean初始化的方法
spring啟動應(yīng)用程序后運行某些邏輯的最簡單方法是將代碼作為所選bean引導(dǎo)過程的一部分來執(zhí)行。
只需創(chuàng)建一個類,將其標(biāo)記為spring組件,并將應(yīng)用程序初始化代碼放在帶有@postconstruct注釋的方法中。理論上,您可以使用構(gòu)造函數(shù)而不是單獨的方法,但將對象的構(gòu)造與其實際責(zé)任分開是一種很好的做法。
1
2
3
4
5
6
7
8
9
10
11
12
|
@component class appinitializator { private static final logger log = loggerfactory.getlogger(appinitializator. class ); @postconstruct private void init() { log.info( "appinitializator initialization logic ..." ); // ... } } |
還可以在主spring boot應(yīng)用程序類中創(chuàng)建一個帶有@postconstruct注釋的方法。不要忘記主類也是框架管理的組件。
1
2
3
4
5
6
7
8
9
10
11
12
|
@springbootapplication public class initdemoapplication { // ... @postconstruct private void init() { log.info( "initdemoapplication initialization logic ..." ); // ... } } |
但這種解決方案感覺就像是一種解決方法而不是真正的解決方案 您可以以非常有限的方式控制spring框架創(chuàng)建應(yīng)用程序bean的順序。如果我們想在創(chuàng)建所有bean之前或甚至在框架啟動之前運行初始化邏輯,我們需要找到更好的東西。
2. spring boot啟動掛鉤
使用spring boot創(chuàng)建的應(yīng)用程序的美妙之處在于,運行它們所需的唯一內(nèi)容是java runtime environment和命令行界面。無需外部工具或應(yīng)用程序。它就像常規(guī)的java se程序一樣運行。
作為每個java程序,您都可以在入口應(yīng)用程序類的靜態(tài)main方法中開始執(zhí)行此類應(yīng)用程序。這就是你可以掛鉤spring boot初始化過程的重點。
首先更改main方法中的代碼,以將啟動掛鉤附加到單獨的方法中。您應(yīng)該在應(yīng)用程序啟動之前添加spring boot掛鉤。
1
2
3
4
5
6
7
8
9
|
public static void main(string[] args) { springapplication application = new springapplication(initdemoapplication. class ); addinithooks(application); application.run(args); } static void addinithooks(springapplication application) { // tbd … } |
當(dāng)spring boot應(yīng)用程序啟動時,它會在引導(dǎo)過程的各個步驟上發(fā)布幾個事件。springapplication類的api公開了一個方法,我們可以使用該方法為這些事件添加偵聽器。
這是一個在spring上下文開始創(chuàng)建bean之前發(fā)布的事件上運行啟動方法的示例:
1
2
3
4
5
6
|
static void addinithooks(springapplication application) { application.addlisteners((applicationlistener<applicationenvironmentpreparedevent>) event -> { string version = event.getenvironment().getproperty( "java.runtime.version" ); log.info( "running with java {}" , version); }); } |
根據(jù)事件類型,spring傳遞給偵聽器的對象可以讓您訪問幾個有用的操作。在前面的示例中,我們讀取了一些環(huán)境屬性,但如果需要,我們也可以修改它。
以下是按啟動時spring boot發(fā)布事件的順序排序的可能事件列表:
- applicationstartingevent
- applicationenvironmentpreparedevent
- applicationcontextinitializedevent
- applicationpreparedevent
- applicationstartedevent
- applicationreadyevent
根據(jù)我的經(jīng)驗,最重要的事件是applicationenvironmentpreparedevent。在spring boot啟動的這個時刻,尚未創(chuàng)建bean,但您可以訪問整個應(yīng)用程序配置。通常,這是運行一些自定義啟動代碼的最佳時機。
3.在啟動時但沒有運行tomcat時運行代碼
盡管spring boot設(shè)計人員在創(chuàng)建框架時考慮了構(gòu)建胖jar,但是一些開發(fā)人員仍然將spring boot應(yīng)用程序部署到常規(guī)的servlet容器(如tomcat)。如果是這種情況,那么前一段中的解決方案將無法發(fā)揮作用。除非有增加額外步驟。
如果將應(yīng)用程序部署為常規(guī)war文件,則可能已經(jīng)擁有springbootservlerinitializator的自定義實現(xiàn)。您只需稍微擴展它并添加初始化掛鉤作為應(yīng)用程序構(gòu)建過程的一部分。
您可以輕松地重用我們在主應(yīng)用程序類中創(chuàng)建的addinithooks()方法。
1
2
3
4
5
6
7
8
9
|
public class initdemowarinitializer extends springbootservletinitializer { @override protected springapplicationbuilder configure(springapplicationbuilder builder) { initdemoapplication.addinithooks(builder.application()); return builder.sources(initdemoapplication. class ); } } |
結(jié)論
簡而言之,在spring boot啟動時運行代碼有兩個主要選項。最簡單的一個設(shè)計用于初始化特定的bean。對于更多全局案例,該框架有一個專用解決方案,可以使用事件偵聽器掛鉤其生命周期。我們學(xué)習(xí)了如何實現(xiàn)和設(shè)置這樣的監(jiān)聽器。
在github存儲庫中找到完全可用的演示
以上就是本文的全部內(nèi)容,希望對大家的學(xué)習(xí)有所幫助,也希望大家多多支持服務(wù)器之家。
原文鏈接:https://www.jdon.com/50872