Spring Boot中的日志抽象確實是SLF4J(Simple Logging Facade for Java)
,它是一個面向Java的簡單日志門面,旨在將各種現(xiàn)有的日志框架映射到基于統(tǒng)一抽象接口的通用API上。
通過使用SLF4J
,應用程序可以將日志記錄器與任何后端日志實現(xiàn)(如Log4j、Logback、Java Util Logging等)進行解耦。這使得在不更改應用程序代碼的情況下,可以輕松地在不同的日志實現(xiàn)之間切換。
(資料圖)
而Spring Boot中默認的日志實現(xiàn)是Logback
,它是由同一作者創(chuàng)建的log4j框架的改進版。Logback是一個功能強大、快速且易于配置的日志框架,它提供了多種日志輸出渠道(包括控制臺、文件、遠程套接字、可插拔的多種數(shù)據(jù)庫支持等),并支持過濾器、多線程等在內(nèi)的一系列高級特性。
當然,你也可以在Spring Boot中使用各種不同的日志框架,比如Log4j2、SLF4j等,只需要在項目中引入對應的依賴,按照對應的配置方式即可。
1、日志的抽象與實現(xiàn)
簡化的日志調(diào)用關(guān)系圖
2、配置文件
2.1、application.properties:logging.config
在 application.properties 文件中,logging.config 屬性用于指定 Logback 配置文件的位置。Logback 是一個流行的 Java 日志框架,它提供了一種靈活的方式來記錄應用程序日志。通過在 application.properties 文件中設置 logging.config 屬性,您可以指定 Logback 配置文件的位置。例如,如果您的 Logback 配置文件名為 logback-spring.xml,并且位于應用程序的根目錄下,則您可以在 application.properties 文件中添加以下行:logging.config=classpath:logback-spring.xml這將告訴 Spring Boot 使用 logback-spring.xml 文件作為 Logback 配置文件。請注意,classpath: 前綴表示該文件位于應用程序的類路徑下。如果您沒有在 application.properties 文件中設置 logging.config 屬性,則 Spring Boot 將使用默認的 Logback 配置。默認情況下,Spring Boot 會在類路徑下查找名為 logback-spring.xml 或 logback.xml 的文件,并使用找到的第一個文件作為 Logback 配置文件。如果找不到任何文件,則 Spring Boot 將使用 Logback 的默認配置。通過使用 logging.config 屬性,您可以輕松地指定 Logback 配置文件的位置,并自定義應用程序的日志記錄行為。在 Spring Boot 中,默認情況下,將使用 Logback 的默認配置。Logback 是一個流行的 Java 日志框架,它提供了一種靈活的方式來記錄應用程序日志。如果您沒有在應用程序中顯式地配置 Logback,則 Spring Boot 將使用 Logback 的默認配置。默認情況下,Logback 的默認配置將日志事件輸出到控制臺,并將日志級別設置為 INFO。如果您需要更改日志記錄行為,則可以在應用程序中配置 Logback,例如通過創(chuàng)建一個名為 logback-spring.xml 的配置文件,并在其中定義附加器、日志記錄器和日志級別等元素。請注意,如果您使用的是 Spring Boot,那么 <shutdownHook> 通常不需要顯式添加,因為 Spring Boot 會自動注冊一個關(guān)閉鉤子來處理日志記錄。但是,在某些情況下,您可能需要手動添加 <shutdownHook> 以確保日志記錄在應用程序關(guān)閉時能夠正常完成。
在Spring Boot中,默認情況下會嘗試從以下幾個位置加載日志配置:
classpath:logback-spring.xml
classpath:logback-spring.groovy
classpath:logback.xml
classpath:logback.groovy
因此,當您沒有在application.properties或application.yml中配置logging.config
屬性時,Spring Boot會按照默認規(guī)則去加載上述配置文件。當然,如果您需要加載的日志配置文件不在默認路徑下,或者除了Logback以外的其他日志實現(xiàn),那么就需要在logging.config
屬性中顯式地指定日志配置文件路徑。
需要注意的是,當存在多個日志配置文件時,Spring Boot會優(yōu)先加載后綴為-spring
的配置文件,這是因為Spring-boot-starter-logging
依賴中封裝了對于Spring的配置的特殊處理,使用該后綴的配置文件可以實現(xiàn)更強的靈活性和擴展性,例如可以引入Spring的屬性占位符。
2.2、application.properties與logback-spring.xml的優(yōu)先級
當在application.properties/application.yml和logback-spring.xml中都配置了同一屬性時(比如logging.level.root
),Spring Boot會優(yōu)先讀取application.properties/application.yml中的配置,而忽略logback-spring.xml中的配置。
這是因為在Spring Boot的日志系統(tǒng)中,logging
屬性優(yōu)先級最高,即使你在 logback-spring.xml
中配置了某個屬性,如果在 application.properties/application.yml
中發(fā)現(xiàn)了同名的屬性,則會覆蓋logback-spring.xml
中的配置。這也是Spring Boot日志配置中logging
屬性優(yōu)先級高于logback-spring.xml中的原因。
因此,在實際應用中,如果您需要對日志輸出級別、使用附加器等進行配置,推薦使用logback-spring.xml這樣的日志配置文件,它可以實現(xiàn)更加靈活和細粒度的配置,而application.properties/application.yml中的配置主要用于簡潔明了的全局配置。
3、logback-spring.xml標簽說明
4、自定義MDC
示例:
這個日志格式中,[,,,]
這一部分表示MDC(Mapped Diagnostic Context),它是一種記錄應用程序信息的機制,在Logback框架和Spring Cloud Sleuth中都有應用。
MDC機制通常用于在系統(tǒng)運行時,記錄一些信息,在日志輸出時將這些信息一并輸出,幫助我們在分析日志時能夠更輕松地定位問題。例如,可以記錄請求ID、用戶IP、客戶端信息等,然后在日志中輸出這些信息,方便跟蹤和排查。
在Spring Cloud Sleuth中,MDC中一般會包含Trace ID、Span ID,代表當前所在的請求鏈路信息,用于服務追蹤和調(diào)用鏈路追蹤。[,,,]
這種空的中括號表示當前日志所在的上下文中沒有設置MDC信息。
需要注意的是,MDC中記錄的信息必須是線程私有的,不同線程之間不能共用MDC。若要在多線程環(huán)境下使用MDC,一般會配合使用ThreadLocal等線程安全的工具。
Logback支持自定義MDC信息??梢酝ㄟ^在代碼中設置MDC,然后在日志輸出時通過%X
占位符輸出MDC中的數(shù)據(jù)。比如:
在上面的代碼中,我們在MDC中添加了一個名為requestId
的鍵值對,然后在日志記錄時使用了%X
占位符將requestId
的值輸出。
在Logback的配置文件中也可以指定每個appender是否包含MDC信息,舉個例子:
在上面的配置中,我們使用了%X{requestId}
來輸出MDC中名為requestId
的鍵的值,將值輸出到日志消息的括號中。
需要注意的是,在Logback中設置MDC信息可能會對性能造成影響,過多或過大的MDC數(shù)據(jù)可能會導致GC times過長等問題。為了避免這些問題,應該盡量精簡MDC信息,只記錄必要的信息。并且,MDC信息應該在不使用時及時清除。
在Spring Cloud Sleuth中,MDC默認記錄Trace ID、Span ID以及Parent Span ID三個值,它們在MDC中用逗號分隔,因此一般情況下,MDC值為3個逗號。
這三個值的具體含義如下:
Trace ID:標識整個請求鏈路的ID,它能夠串聯(lián)整個請求鏈路中的所有Span。
Span ID:標識當前Span的ID,以區(qū)分一個Trace中包含的不同Span。
Parent Span ID:與Span ID一起使用,標識當前Span的父級Span ID。
這三個值在Spring Cloud Sleuth中都是使用UUID生成的唯一標識符。在日志輸出時,可以使用%X{traceId}
、%X{spanId}
、%X{parentId}
這些占位符輸出這些值。
如果你在輸出日志時,發(fā)現(xiàn)MDC值不是三個逗號,而是其他的分隔符,或者對應的值不是UUID,這可能是因為自己修改了配置導致的,可以查看一下配置文件和相關(guān)代碼來進行排查。
這個日志格式中的 true
表示是否已經(jīng)記錄了正確的MDC值,即Trace ID、Span ID以及Parent Span ID三個值。當為true時,表示MDC中已記錄了這三個值,并且這些值可以跨度傳播至請求鏈中的下游調(diào)用。如果值為false,則可能意味著MDC沒有設置好,或者日志記錄器沒有正確的配置。
最近更新