spring-boot 3.4以降 (2025/6/3 追記)
https://kagamihoge.hatenablog.com/entry/2025/06/03/165344
基本的な使い方のサンプルコード
plugins {
id 'java'
id 'org.springframework.boot' version '3.3.1'
id 'io.spring.dependency-management' version '1.1.5'
}
group = 'com.example'
version = '0.0.1-SNAPSHOT'
java {
toolchain {
languageVersion = JavaLanguageVersion.of(17)
}
}
configurations {
compileOnly {
extendsFrom annotationProcessor
}
}
repositories {
mavenCentral()
}
dependencies {
implementation 'org.springframework.boot:spring-boot-starter-web'
implementation 'net.logstash.logback:logstash-logback-encoder:7.4'
compileOnly 'org.projectlombok:lombok'
annotationProcessor 'org.projectlombok:lombok'
testImplementation 'org.springframework.boot:spring-boot-starter-test'
testRuntimeOnly 'org.junit.platform:junit-platform-launcher'
}
tasks.named('test') {
useJUnitPlatform()
}
logstash-logback-encoderのバージョンはspring-boot、というより、これに含まれるlogbackに合わせる必要がある……らしい。詳細は https://github.com/logfellow/logstash-logback-encoder?tab=readme-ov-file#including-it-in-your-project にある。問題があると実行時にClassNotFoundExceptionなどが発生したりするらしい。
src/main/resources/logback-spring.xml を作成する。
<?xml version="1.0" encoding="UTF-8"?> <configuration> <appender name="CONSOLE" class="ch.qos.logback.core.ConsoleAppender"> <encoder class="net.logstash.logback.encoder.LogstashEncoder"> </encoder> </appender> <root level="INFO"> <appender-ref ref="CONSOLE"/> </root> </configuration>
動作確認用の適当なRestControllerを作成する。
@SpringBootApplication @RestController @Slf4j public class App { @GetMapping("/test") public String ho() { log.info("info"); log.error("", new NullPointerException("error")); return "sad"; } public static void main(String[] args) { SpringApplication.run(App.class, args); } }
これでログがjsonになるが、開発中は見やすく整形して表示する設定を追加する。
<encoder class="net.logstash.logback.encoder.LogstashEncoder"> <jsonGeneratorDecorator class="net.logstash.logback.decorate.PrettyPrintingJsonGeneratorDecorator"/> ...(略)
実行例。
{ "@timestamp" : "2024-07-14T19:58:24.6156441+09:00", "@version" : "1", "message" : "info", "logger_name" : "org.example.app.App", "thread_name" : "http-nio-8080-exec-6", "level" : "INFO", "level_value" : 20000 } { "@timestamp" : "2024-07-14T19:58:24.6156441+09:00", "@version" : "1", "message" : "", "logger_name" : "org.example.app.App", "thread_name" : "http-nio-8080-exec-6", "level" : "ERROR", "level_value" : 40000, "stack_trace" : "java.lang.NullPointerException: error\r\n\t(略)" }
LoggingEvent
上記を基本形にドキュメントみながらあれこれ修正を加えていく。ここでは幾つかのみ触れる。
https://github.com/logfellow/logstash-logback-encoder?tab=readme-ov-file#loggingevent-fields
フィールド名の変更
<appender name="CONSOLE" class="ch.qos.logback.core.ConsoleAppender"> <encoder class="net.logstash.logback.encoder.LogstashEncoder"> <jsonGeneratorDecorator class="net.logstash.logback.decorate.PrettyPrintingJsonGeneratorDecorator"/> <fieldNames> <timestamp>時間</timestamp> <stackTrace>stacktrace</stackTrace> </fieldNames> </encoder> </appender>
試しに日本語にしてみたが特に意味はない。
{ "時間" : "2024-07-13T19:12:05.2237172+09:00", (略) "stacktrace" : "java.lang.NullPointerException: (略)" }
key-valueでフィールド追加
https://github.com/logfellow/logstash-logback-encoder?tab=readme-ov-file#key-value-pair-fields
https://www.slf4j.org/manual.html#fluent とかいうのでkey/valueペアを仕込める。以下のようにすると、
log.atInfo().addKeyValue("fluent-key", "fluent-value").setMessage("fluent-msg").log();
以下のようなフィールドが追加される。
"fluent-key" : "fluent-value"
以下のようにしてinclude/excludeを切り替えられる。たいていの項目は<exclude...>, <include...>という形式で切り替えられる。
<excludeKeyValueKeyName>fluent-key</excludeKeyValueKeyName>
この設定項目に関しては以下で全部出なくなる。
<includeKeyValuePairs>false</includeKeyValuePairs>
StructuredArguments/Markers
StructuredArguments, Markers でフィールド追加できる。細かい違いについては上記ドキュメントを参照。
StructuredArgumentsの例。
log.info("log message {}", StructuredArguments.value("name", "value"));
"message" : "log message value", "name" : "value",
Markersの例。
log.info(Markers.append("marker-name", "v"), "log");
"message" : "log", "marker-name" : "v",
LoggingEventCompositeJsonEncoder でより細かくJSONフォーマットを指定
https://github.com/logfellow/logstash-logback-encoder?tab=readme-ov-file#composite-encoderlayout
以下は使用例。%.. は https://logback.qos.ch/manual/layouts.html#ClassicPatternLayout を参照。
<encoder class="net.logstash.logback.encoder.LoggingEventCompositeJsonEncoder"> <providers> <timestamp/> <pattern> <pattern> { "message": "%msg", "exception-message": "%ex{0}" } </pattern> </pattern> </providers> </encoder>
実行例。
{"@timestamp":"2024-07-14T20:33:21.110684+09:00","message":"info","exception-message":""} {"@timestamp":"2024-07-14T20:33:21.110684+09:00","message":"","exception-message":"java.lang.NullPointerException: error\r\n"}