私のJavaアプリケーションをドッカーに入れるつもりです。しかし、私たちの会社のロギング施設に基づいて、私はfluentd
を使ってコンテナのログを収集しなければなりません。それで私はJavaスタックトレースを1行のログに入れなければなりません。ドックのlogbackによる1行でのprint java例外の問題
私は以下のことをしましたが、状況によっては動作しますが、お互いに失敗します。
package com.alex;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.util.zip.DataFormatException;
public class Main {
private static final Logger logger = LoggerFactory.getLogger(Main.class);
public static void alexExc() throws Exception {
throw new Exception("hello");
}
public static void main(String[] args) throws Exception {
try {
alexExc();
} catch (Throwable t) {
logger.error("oops", t);
}
throw new DataFormatException("invalid data format");
}
}
次は私の指定された一つの "#012"
package com.alex;
import ch.qos.logback.classic.pattern.ThrowableProxyConverter;
import ch.qos.logback.classic.spi.IThrowableProxy;
import ch.qos.logback.core.CoreConstants;
public class OneLineStackTraceConverter extends ThrowableProxyConverter {
protected String throwableProxyToString(IThrowableProxy tp) {
String originalStackTrace = super.throwableProxyToString(tp);
return originalStackTrace.replace(CoreConstants.LINE_SEPARATOR, " #012");
}
}
で区切りを置き換えるために、私のコンバータである。そして、私のlogback設定です:あなたが見ることができるように
<?xml version="1.0" encoding="UTF-8" ?>
<configuration scan="true" scanPeriod="30 seconds">
<conversionRule conversionWord="ex"
converterClass="com.alex.OneLineStackTraceConverter" />
<appender name="INFO_FILE"
class="ch.qos.logback.core.rolling.RollingFileAppender">
<file>/logs/loggingmdc/info.log</file>
<rollingPolicy class="ch.qos.logback.core.rolling.FixedWindowRollingPolicy">
<fileNamePattern>/logs/loggingmdc/info.log.%i</fileNamePattern>
<minIndex>1</minIndex>
<maxIndex>5</maxIndex>
</rollingPolicy>
<triggeringPolicy
class="ch.qos.logback.core.rolling.SizeBasedTriggeringPolicy">
<maxFileSize>1GB</maxFileSize>
</triggeringPolicy>
<encoder>
<pattern>%d{yyyy-MM-dd HH:mm:ss.SSS} %le %logger{0}: ## %msg\n</pattern>
</encoder>
<filter class="ch.qos.logback.classic.filter.LevelFilter">
<level>INFO</level>
<onMatch>ACCEPT</onMatch>
<onMismatch>DENY</onMismatch>
</filter>
</appender>
<appender name="DEBUG_FILE"
class="ch.qos.logback.core.rolling.RollingFileAppender">
<file>/logs/loggingmdc/debug.log</file>
<rollingPolicy class="ch.qos.logback.core.rolling.FixedWindowRollingPolicy">
<fileNamePattern>/logs/loggingmdc/debug.log.%i</fileNamePattern>
<minIndex>1</minIndex>
<maxIndex>5</maxIndex>
</rollingPolicy>
<triggeringPolicy
class="ch.qos.logback.core.rolling.SizeBasedTriggeringPolicy">
<maxFileSize>1GB</maxFileSize>
</triggeringPolicy>
<encoder>
<pattern>%d{yyyy-MM-dd HH:mm:ss.SSS} %le %logger{0}: ## %msg %ex\n</pattern>
</encoder>
<filter class="ch.qos.logback.classic.filter.LevelFilter">
<level>DEBUG</level>
<onMatch>ACCEPT</onMatch>
<onMismatch>DENY</onMismatch>
</filter>
</appender>
<appender name="ERROR_FILE"
class="ch.qos.logback.core.rolling.RollingFileAppender">
<file>/logs/loggingmdc/error.log</file>
<rollingPolicy class="ch.qos.logback.core.rolling.FixedWindowRollingPolicy">
<fileNamePattern>/logs/loggingmdc/error.log.%i</fileNamePattern>
<minIndex>1</minIndex>
<maxIndex>5</maxIndex>
</rollingPolicy>
<triggeringPolicy
class="ch.qos.logback.core.rolling.SizeBasedTriggeringPolicy">
<maxFileSize>1GB</maxFileSize>
</triggeringPolicy>
<encoder>
<pattern>%d{yyyy-MM-dd HH:mm:ss.SSS} %le %logger{0}: ## %msg %ex\n</pattern>
</encoder>
<filter class="ch.qos.logback.classic.filter.LevelFilter">
<level>ERROR</level>
<onMatch>ACCEPT</onMatch>
<onMismatch>DENY</onMismatch>
</filter>
</appender>
<appender name="THIRD_PARTY_FILE"
class="ch.qos.logback.core.rolling.RollingFileAppender">
<file>/logs/loggingmdc/thirdparty.log</file>
<rollingPolicy class="ch.qos.logback.core.rolling.FixedWindowRollingPolicy">
<fileNamePattern>/logs/loggingmdc/thirdparty.log.%i</fileNamePattern>
<minIndex>1</minIndex>
<maxIndex>5</maxIndex>
</rollingPolicy>
<triggeringPolicy
class="ch.qos.logback.core.rolling.SizeBasedTriggeringPolicy">
<maxFileSize>1GB</maxFileSize>
</triggeringPolicy>
<encoder>
<pattern>%d{yyyy-MM-dd HH:mm:ss.SSS} %le %logger{0}: ## %msg %ex\n</pattern>
</encoder>
</appender>
<root level="INFO">
<appender-ref ref="THIRD_PARTY_FILE"/>
</root>
<logger name="com.alex" level="DEBUG" additivity="false">
<appender-ref ref="INFO_FILE"/>
<appender-ref ref="DEBUG_FILE"/>
<appender-ref ref="ERROR_FILE"/>
</logger>
</configuration>
私のログバック設定では、私はconversionRule
を追加して、イベントログ中の例外が私のOneLineStackTraceConverter
を使用することを指定します。
- それは私が私のエンコーダ
- ため、各パターンに
%ex
が含まれている場合、私はパターンで%ex
を含めるDONOT場合、それは動作しません動作します。どうして?ユーザーがパターンに%ex
を含めることを忘れた場合、その例外に使用する他のconversionWordがありますか? - 最後の
DataFormatException
はログファイルには載っていませんが、コンソールに出力されます。コンソールにもログファイルがあります。どうすればそれをすることができますか?
ありがとうございます。
ご返信ありがとうございます。最初のものについては、あなたが説明したことを正確に理解しています。しかし、パターンに '%ex'を使用すると、スタックトレースは1行にフォーマットされていることが期待されます。パターンで '%ex'を削除すると、スタックトレースもログファイルにありますが、指定されたコンバータを使用していない元の複数行のスタックトレースです。もう1つは、ログファイルにも例外を指示する方法がありますか? – Alex
@Alex 1)ログバックは、ログステートメントとパターンを一致させます。ログ文にカスタムパーサを指定しないと、メッセージの一部としてアペンダにダンプされます。これは、正規表現のマッチングに似ています - 指定した部分だけがマッチします。 2)コンソールアペンダーを宣言し、fluentdを使ってDockerログをポンピングすることもできます。 –