Der*_*har 147 java logging logback
如何配置Logback以将记录器的不同级别记录到不同的目标?
例如,给定以下Logback配置,Logback会将INFO
消息记录到STDOUT
和ERROR
消息STDERR
吗?
(请注意,此示例是第3章:Logback配置中logback-examples/src/main/java/chapters/configuration/sample4.xml
显示的示例的变体).
<configuration>
<appender name="STDOUT"
class="ch.qos.logback.core.ConsoleAppender">
<encoder>
<pattern>
%d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n
</pattern>
</encoder>
</appender>
<appender name="STDERR"
class="ch.qos.logback.core.ConsoleAppender">
<encoder>
<pattern>
%d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n
</pattern>
</encoder>
<target>System.err</target>
</appender>
<!-- What is the effective level of "chapters.configuration"? -->
<logger name="chapters.configuration" level="INFO" additivity="false">
<appender-ref ref="STDOUT" />
</logger>
<logger name="chapters.configuration" level="ERROR" additivity="false">
<appender-ref ref="STDERR" />
</logger>
<!-- turn OFF all logging (children can override) -->
<root level="OFF">
<appender-ref ref="STDOUT" />
</root>
</configuration>
Run Code Online (Sandbox Code Playgroud)
buy*_*ies 82
我相信这将是最简单的解决方案:
<configuration>
<contextName>selenium-plugin</contextName>
<!-- Logging configuration -->
<appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
<Target>System.out</Target>
<filter class="ch.qos.logback.classic.filter.LevelFilter">
<level>INFO</level>
<onMatch>ACCEPT</onMatch>
<onMismatch>DENY</onMismatch>
</filter>
<encoder>
<pattern>[%d{yyyy-MM-dd HH:mm:ss.SSS}] [%level] %msg%n</pattern>
</encoder>
</appender>
<appender name="STDERR" class="ch.qos.logback.core.ConsoleAppender">
<Target>System.err</Target>
<filter class="ch.qos.logback.classic.filter.LevelFilter">
<level>ERROR</level>
<onMatch>ACCEPT</onMatch>
<onMismatch>DENY</onMismatch>
</filter>
<encoder>
<pattern>[%d{yyyy-MM-dd HH:mm:ss.SSS}] [%level] [%thread] %logger{10} [%file:%line] %msg%n</pattern>
</encoder>
</appender>
<root level="INFO">
<appender-ref ref="STDOUT"/>
<appender-ref ref="STDERR" />
</root>
</configuration>
Run Code Online (Sandbox Code Playgroud)
Uri*_*ter 61
更新:对于使用Groovy的所有基于配置的方法,请参阅Dean Hiller的回答.
-
你可以使用Logback过滤器做一些有趣的事情.以下配置只会向stderr打印警告和错误消息,并将其他所有内容打印到stdout.
logback.xml
<appender name="stdout" class="ch.qos.logback.core.ConsoleAppender">
<target>System.out</target>
<filter class="com.foo.StdOutFilter" />
...
</appender>
<appender name="stderr" class="ch.qos.logback.core.ConsoleAppender">
<target>System.err</target>
<filter class="com.foo.ErrOutFilter" />
...
</appender>
<logger name="mylogger" level="debug">
<appender-ref ref="stdout" />
<appender-ref ref="stderr" />
</logger>
Run Code Online (Sandbox Code Playgroud)
com.foo.StdOutFilter
public class StdOutFilter extends ch.qos.logback.core.filter.AbstractMatcherFilter
{
@Override
public FilterReply decide(Object event)
{
if (!isStarted())
{
return FilterReply.NEUTRAL;
}
LoggingEvent loggingEvent = (LoggingEvent) event;
List<Level> eventsToKeep = Arrays.asList(Level.TRACE, Level.DEBUG, Level.INFO);
if (eventsToKeep.contains(loggingEvent.getLevel()))
{
return FilterReply.NEUTRAL;
}
else
{
return FilterReply.DENY;
}
}
}
Run Code Online (Sandbox Code Playgroud)
com.foo.ErrOutFilter
public class ErrOutFilter extends ch.qos.logback.core.filter.AbstractMatcherFilter
{
@Override
public FilterReply decide(Object event)
{
if (!isStarted())
{
return FilterReply.NEUTRAL;
}
LoggingEvent loggingEvent = (LoggingEvent) event;
List<Level> eventsToKeep = Arrays.asList(Level.WARN, Level.ERROR);
if (eventsToKeep.contains(loggingEvent.getLevel()))
{
return FilterReply.NEUTRAL;
}
else
{
return FilterReply.DENY;
}
}
}
Run Code Online (Sandbox Code Playgroud)
Séb*_*ert 40
解决方案仅基于配置,使用ThresoldFilter和LevelFilters来使事情变得非常简单:
<configuration>
<appender name="STDERR" class="ch.qos.logback.core.ConsoleAppender">
<target>System.err</target>
<filter class="ch.qos.logback.classic.filter.ThresholdFilter">
<level>WARN</level>
</filter>
<encoder>
<pattern>%date %level [%thread] %logger %msg%n</pattern>
</encoder>
</appender>
<appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
<target>System.out</target>
<filter class="ch.qos.logback.classic.filter.LevelFilter">
<level>DEBUG</level>
<onMatch>ACCEPT</onMatch>
</filter>
<filter class="ch.qos.logback.classic.filter.LevelFilter">
<level>INFO</level>
<onMatch>ACCEPT</onMatch>
</filter>
<filter class="ch.qos.logback.classic.filter.LevelFilter">
<level>TRACE</level>
<onMatch>ACCEPT</onMatch>
</filter>
<filter class="ch.qos.logback.classic.filter.LevelFilter">
<level>WARN</level>
<onMatch>DENY</onMatch>
</filter>
<filter class="ch.qos.logback.classic.filter.LevelFilter">
<level>ERROR</level>
<onMatch>DENY</onMatch>
</filter>
<encoder>
<pattern>%date %level [%thread] %logger %msg%n</pattern>
</encoder>
</appender>
<root level="INFO">
<appender-ref ref="STDOUT" />
<appender-ref ref="STDERR" />
</root>
</configuration>
Run Code Online (Sandbox Code Playgroud)
Dea*_*ler 31
好的,这是我最喜欢的xml方式.我为eclipse版本这样做,所以我可以
由于某种原因,SO没有正确显示这一切,但大多数似乎都在那里......
<configuration scan="true" scanPeriod="30 seconds">
<appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
<filter class="ch.qos.logback.core.filter.EvaluatorFilter">
<evaluator class="ch.qos.logback.classic.boolex.GEventEvaluator">
<expression>
e.level.toInt() <= INFO.toInt()
</expression>
</evaluator>
<OnMismatch>DENY</OnMismatch>
<OnMatch>NEUTRAL</OnMatch>
</filter>
<encoder>
<pattern>%date{ISO8601} %X{sessionid}-%X{user} %caller{1} %-4level: %message%n</pattern>
</encoder>
</appender>
<appender name="STDERR" class="ch.qos.logback.core.ConsoleAppender">
<filter class="ch.qos.logback.classic.filter.ThresholdFilter">
<level>warn</level>
</filter>
<encoder>
<pattern>%date{ISO8601} %X{sessionid}-%X{user} %caller{1} %-4level: %message%n</pattern>
</encoder>
<target>System.err</target>
</appender>
<root>
<level value="INFO" />
<appender-ref ref="STDOUT"/>
<appender-ref ref="STDERR"/>
</root>
</configuration>
Run Code Online (Sandbox Code Playgroud)
X. *_*tuk 13
最简单的解决方案是ThresholdFilter
在appender 上使用:
<appender name="..." class="...">
<filter class="ch.qos.logback.classic.filter.ThresholdFilter">
<level>INFO</level>
</filter>
Run Code Online (Sandbox Code Playgroud)
完整示例:
<configuration>
<appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
<filter class="ch.qos.logback.classic.filter.ThresholdFilter">
<level>INFO</level>
</filter>
<encoder>
<pattern>%d %-5level: %msg%n</pattern>
</encoder>
</appender>
<appender name="STDERR" class="ch.qos.logback.core.ConsoleAppender">
<filter class="ch.qos.logback.classic.filter.ThresholdFilter">
<level>ERROR</level>
</filter>
<target>System.err</target>
<encoder>
<pattern>%d %-5level: %msg%n</pattern>
</encoder>
</appender>
<root>
<appender-ref ref="STDOUT" />
<appender-ref ref="STDERR" />
</root>
</configuration>
Run Code Online (Sandbox Code Playgroud)
更新:正如迈克在评论中指出的那样,ERROR级别的消息都打印在STDOUT和STDERR上.但不确定OP的意图是什么.如果这不是你想要的,你可以试试迈克的答案.
小智 10
这是我使用的配置,工作正常,它基于XML + JaninoEventEvaluator(需要将Janino库添加到Classpath)
<configuration>
<appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
<encoder>
<pattern>%date | [%-5level] in [%file:%line] - %msg %n</pattern>
</encoder>
<filter class="ch.qos.logback.core.filter.EvaluatorFilter">
<evaluator class="ch.qos.logback.classic.boolex.JaninoEventEvaluator">
<expression>
level <= INFO
</expression>
</evaluator>
<OnMismatch>DENY</OnMismatch>
<OnMatch>NEUTRAL</OnMatch>
</filter>
</appender>
<appender name="STDERR" class="ch.qos.logback.core.ConsoleAppender">
<target>System.err</target>
<encoder>
<pattern>%date | [%-5level] in [%file:%line] - %msg %n</pattern>
</encoder>
<filter class="ch.qos.logback.classic.filter.ThresholdFilter">
<level>WARN</level>
</filter>
</appender>
<root level="DEBUG">
<appender-ref ref="STDOUT" />
<appender-ref ref="STDERR" />
</root>
</configuration>
Run Code Online (Sandbox Code Playgroud)
我使用logback.groovy配置我的logback,但你也可以使用xml配置:
import static ch.qos.logback.classic.Level.*
import static ch.qos.logback.core.spi.FilterReply.DENY
import static ch.qos.logback.core.spi.FilterReply.NEUTRAL
import ch.qos.logback.classic.boolex.GEventEvaluator
import ch.qos.logback.classic.encoder.PatternLayoutEncoder
import ch.qos.logback.core.ConsoleAppender
import ch.qos.logback.core.filter.EvaluatorFilter
def patternExpression = "%date{ISO8601} [%5level] %msg%n"
appender("STDERR", ConsoleAppender) {
filter(EvaluatorFilter) {
evaluator(GEventEvaluator) {
expression = 'e.level.toInt() >= WARN.toInt()'
}
onMatch = NEUTRAL
onMismatch = DENY
}
encoder(PatternLayoutEncoder) {
pattern = patternExpression
}
target = "System.err"
}
appender("STDOUT", ConsoleAppender) {
filter(EvaluatorFilter) {
evaluator(GEventEvaluator) {
expression = 'e.level.toInt() < WARN.toInt()'
}
onMismatch = DENY
onMatch = NEUTRAL
}
encoder(PatternLayoutEncoder) {
pattern = patternExpression
}
target = "System.out"
}
logger("org.hibernate.type", WARN)
logger("org.hibernate", WARN)
logger("org.springframework", WARN)
root(INFO,["STDERR","STDOUT"])
Run Code Online (Sandbox Code Playgroud)
我认为使用GEventEvaluator更简单,因为不需要创建过滤器类.
我为我的英语道歉!
我不相信这个答案,因为它只是上面最好的两个答案的组合:X. Wo Satuk 的那个和 Sébastien Helbert 的那个:ThresholdFilter
很可爱,但你不能将它配置为具有上层和较低的水平*,但它有两个合并LevelFilters
设置为“拒绝”WARN
和ERROR
工作的享受。
非常重要:不要忘记<target>System.err</target>
STDERR 附加程序中的标签:我对它的遗漏让我沮丧了几分钟。
<configuration>
<timestamp key="byDay" datePattern="yyyyMMdd'T'HHmmss" />
<appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
<filter class="ch.qos.logback.classic.filter.ThresholdFilter">
<level>INFO</level>
</filter>
<filter class="ch.qos.logback.classic.filter.LevelFilter">
<level>WARN</level>
<onMatch>DENY</onMatch>
</filter>
<filter class="ch.qos.logback.classic.filter.LevelFilter">
<level>ERROR</level>
<onMatch>DENY</onMatch>
</filter>
<encoder>
<pattern>%d{HH:mm:ss.SSS} [%thread] %-5level %logger{36}.%M\(%line\)
- %msg%n
</pattern>
</encoder>
</appender>
<appender name="STDERR" class="ch.qos.logback.core.ConsoleAppender">
<filter class="ch.qos.logback.classic.filter.ThresholdFilter">
<level>WARN</level>
</filter>
<target>System.err</target>
<encoder>
<pattern>%d{HH:mm:ss.SSS} [%thread] %-5level %logger{36}.%M\(%line\)
- %msg%n
</pattern>
</encoder>
</appender>
<root level="debug">
<appender-ref ref="STDOUT" />
<appender-ref ref="STDERR" />
</root>
</configuration>
Run Code Online (Sandbox Code Playgroud)
* 然而,它确实decide
在API 中有一个方法,但我不知道你会如何在这种情况下使用它。
尝试这个。您可以只使用内置的ThresholdFilter
和LevelFilter
。无需以编程方式创建自己的过滤器。在此示例中,WARN 和 ERROR 级别记录到 System.err,其余级别记录到 System.out:
<appender name="stdout" class="ch.qos.logback.core.ConsoleAppender">
<!-- deny ERROR level -->
<filter class="ch.qos.logback.classic.filter.LevelFilter">
<level>ERROR</level>
<onMatch>DENY</onMatch>
</filter>
<!-- deny WARN level -->
<filter class="ch.qos.logback.classic.filter.LevelFilter">
<level>WARN</level>
<onMatch>DENY</onMatch>
</filter>
<target>System.out</target>
<immediateFlush>true</immediateFlush>
<encoder>
<charset>utf-8</charset>
<pattern>${msg_pattern}</pattern>
</encoder>
</appender>
<appender name="stderr" class="ch.qos.logback.core.ConsoleAppender">
<!-- deny all events with a level below WARN, that is INFO, DEBUG and TRACE -->
<filter class="ch.qos.logback.classic.filter.ThresholdFilter">
<level>WARN</level>
</filter>
<target>System.err</target>
<immediateFlush>true</immediateFlush>
<encoder>
<charset>utf-8</charset>
<pattern>${msg_pattern}</pattern>
</encoder>
</appender>
<root level="WARN">
<appender-ref ref="stderr"/>
</root>
<root level="TRACE">
<appender-ref ref="stdout"/>
</root>
Run Code Online (Sandbox Code Playgroud)
归档时间: |
|
查看次数: |
134622 次 |
最近记录: |