<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.mycompany</groupId>
<artifactId>SLF4JExam</artifactId>
<version>1.0-SNAPSHOT</version>
<packaging>jar</packaging>
<name>SLF4JExam</name>
<url>http://maven.apache.org</url>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties>
<dependencies>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.11</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-log4j12</artifactId>
<version>1.7.2</version>
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-ext</artifactId>
<version>1.7.2</version>
</dependency>
</dependencies>
</project>
package com.mycompany.slf4jexam;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.slf4j.MDC;
import org.slf4j.Marker;
import org.slf4j.MarkerFactory;
public class App {
public static void main(String[] args) {
Logger logger = LoggerFactory.getLogger(App.class);
// バインドしているログフレームワークのマップ化コンテキストと連携
// Log 用の ThreadLocal な Map
// Log4j の MDC に対応 (NDC((スタック))に対応する者は無い)
MDC.put("uid", "USER01234");
logger.trace("Hello Trace");
logger.debug("Hello Debug");
logger.warn("Hello Warn");
logger.info("Hello Info");
logger.error("Hello Error");
// fatal は無い
logger.info("\\{} はプレースホルダ => {} is not {}", 1, 2);
logger.info("\\{} に順版を指定できない => {1} is not {0}", 1, 2);
try {
throw new NullPointerException("ぬるぽ");
} catch (NullPointerException e) {
// logback では、設定ファイルで Marker によって出力する・しないのフィルタリングができる
// たとえば ERROR レベルで、syslogMarker マーカーのついているログだけ、SYSLOG に出力して
// 運用監視するとか
//
// <turboFilter class="ch.qos.logback.classic.turbo.MarkerFilter">
// <Marker>REPORT</Marker>
// <OnMatch>ACCEPT</OnMatch>
// </turboFilter>
Marker syslogMarker = MarkerFactory.getMarker("REPORT");
logger.error(syslogMarker, "エラーが発生しました", e); // 引数に throwable を入れるとスタックトレースが出る
}
// MDC は、処理終了時に必ず clear() する
// (特に Web アプリなどで ThreadPool で Thread が使いまわされる可能性があるので)
MDC.clear();
}
}
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE log4j:configuration SYSTEM "log4j.dtd">
<log4j:configuration xmlns:log4j='http://jakarta.apache.org/log4j/'>
<!-- ********************** 標準出力への出力 ********************** -->
<appender name="STDOUT" class="org.apache.log4j.ConsoleAppender">
<param name="threshold" value="trace" />
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern"
value="%d{yyyy-MMM-dd HH:mm:ss.SSS} : %-5p : %X{uid} : %m%n" />
</layout>
</appender>
<!-- ********************** /dev/nullへの出力 ********************** -->
<appender name="NULL" class="org.apache.log4j.varia.NullAppender">
<param name="threshold" value="fatal"/>
</appender>
<!-- ********************** com.mycompany.slf4jexam.* のログは、STDOUT へ ********************** -->
<logger name="com.mycompany.slf4jexam" additivity="false"> <!-- root および 包含するパッケージの category の設定を継承しない -->
<level value="trace" />
<appender-ref ref="STDOUT" />
</logger >
<!-- ********************** その他(ライブラリなど)は NULL へ ********************** -->
<root>
<priority value="warn" />
<appender-ref ref="NULL" />
</root>
</log4j:configuration>
2013-2-08 01:27:20.056 : TRACE : USER01234 : Hello Trace 2013-2-08 01:27:20.058 : DEBUG : USER01234 : Hello Debug 2013-2-08 01:27:20.058 : WARN : USER01234 : Hello Warn 2013-2-08 01:27:20.058 : INFO : USER01234 : Hello Info 2013-2-08 01:27:20.058 : ERROR : USER01234 : Hello Error 2013-2-08 01:27:20.063 : INFO : USER01234 : {} はプレースホルダ => 1 is not 2 2013-2-08 01:27:20.063 : INFO : USER01234 : {} に順版を指定できない => {1} is not {0} 2013-2-08 01:27:20.070 : ERROR : USER01234 : エラーが発生しました java.lang.NullPointerException: ぬるぽ at com.mycompany.slf4jexam.App.main(App.java:33)
slf4j-ext にある LocLogger? を使う。メッセージのキーは enum で定義し、各国語のプロパティファイルでテンプレートを管理する
package com.mycompany.slf4jexam;
import java.util.Locale;
import org.slf4j.cal10n.LocLogger;
public class App2 {
public static void main(String[] args) {
LocLogger logger = MyLoggerFactory.getLogger(App.class);
logger.info(Msg.INFORM_START_ACTION, "TEST");
// LocLogger で、外部定義のメッセージテンプレートを使うときには、
// プレースホルダに順番を設定できる {0} is {1}
logger.warn(Msg.BIZERR_RESERVE_SHORTAGE, "Mario Bros. Co.", 18000);
// メッセージテンプレートが即値の場合には Logger とおなじ
logger.debug("顧客ID={}, 売掛金={}, 回収金={}", 01234, 141400, 123400);
logger.info(Msg.INFORM_END_ACTION, "TEST");
LocLogger logger2 = MyLoggerFactory.getLogger(App.class, Locale.UK);
logger2.info(Msg.INFORM_START_ACTION, "TEST");
logger2.warn(Msg.BIZERR_RESERVE_SHORTAGE, "Mario Bros. Co.", 18000);
logger.debug("customer_id={}, book_credit={}, claw_back={}", 01234, 141400, 123400);
logger2.info(Msg.INFORM_END_ACTION, "TEST");
}
}
package com.mycompany.slf4jexam;
import ch.qos.cal10n.BaseName;
import ch.qos.cal10n.Locale;
import ch.qos.cal10n.LocaleData;
@BaseName("template")
@LocaleData( { @Locale("en_UK"), @Locale("ja_JP") })
public enum Msg {
SYSERR_CANNOT_CONNECT_DB,
BIZERR_RESERVE_SHORTAGE,
INFORM_START_ACTION,
INFORM_END_ACTION
}
package com.mycompany.slf4jexam;
import ch.qos.cal10n.IMessageConveyor;
import ch.qos.cal10n.MessageConveyor;
import java.util.Locale;
import org.slf4j.cal10n.LocLogger;
import org.slf4j.cal10n.LocLoggerFactory;
public class MyLoggerFactory {
public static LocLogger getLogger(Class clazz) {
return getLogger(clazz, Locale.getDefault());
}
public static LocLogger getLogger(Class clazz, Locale locale) {
IMessageConveyor messageConveyor = new MessageConveyor(locale);
LocLoggerFactory factory = new LocLoggerFactory(messageConveyor);
return factory.getLocLogger(clazz);
}
}
SYSERR_CANNOT_CONNECT_DB=データベース接続エラー PORT={0}, SID={1} BIZERR_RESERVE_SHORTAGE={0} 向けの債権の引き当てができません。 {1} ドル不足しています INFORM_START_ACTION={0} 業務開始 INFORM_END_ACTION={0} 業務終了
SYSERR_CANNOT_CONNECT_DB=DB Connection Error PORT={0}, SID={1} BIZERR_RESERVE_SHORTAGE=the loans of {0} will not be covered by its loan-loss reserves. ${1} shortage. INFORM_START_ACTION=START {0} INFORM_END_ACTION=END {0}
NetBeans? いかす
2013-2-08 01:36:58.615 : INFO : : TEST 業務開始 2013-2-08 01:36:58.621 : WARN : : Mario Bros. Co. 向けの債権の引き当てができません。 18,000 ドル不足しています 2013-2-08 01:36:58.624 : DEBUG : : 顧客ID=668, 売掛金=141400, 回収金=123400 2013-2-08 01:36:58.624 : INFO : : TEST 業務終了 2013-2-08 01:36:58.627 : INFO : : START TEST 2013-2-08 01:36:58.628 : WARN : : the loans of Mario Bros. Co. will not be covered by its loan-loss reserves. $18,000 shortage. 2013-2-08 01:36:58.628 : DEBUG : : customer_id=668, book_credit=141400, claw_back=123400 2013-2-08 01:36:58.628 : INFO : : END TEST