我正在尝试更多地理解logback
,并编写了一个非常简单的独立Java应用程序-helloworld:
package com.example;
import java.io.IOException;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import ch.qos.logback.classic.LoggerContext;
import ch.qos.logback.core.util.StatusPrinter;
public class Slf4jApp1 {
private static final Logger LOGGER = LoggerFactory.getLogger(Slf4jApp1.class);
public static void main(String[] args) throws InterruptedException, IOException {
LOGGER.info("Hello World");
for (;;)
;
}
}
下面是logback.xml
<?xml version="1.0" encoding="UTF-8"?>
<configuration scan="true" scanPeriod="60 seconds">
<appender name="STDOUT"
class="ch.qos.logback.core.ConsoleAppender">
<encoder>
<!-- %d{yyyy-MM-dd HH:mm:ss.SSS} %thread %-5level %logger{0}:%L
If you required class name ,enable %logger{0}:%L -->
<pattern>%d{yyyy-MM-dd HH:mm:ss.SSS} %thread %-5level - %msg
%n</pattern>
</encoder>
</appender>
<appender name="FILE"
class="ch.qos.logback.core.rolling.RollingFileAppender">
<file>/Users/user1/eclipse-workspace/logback-learning/log-file.log
</file>
<append>true</append>
<rollingPolicy
class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
<fileNamePattern>/Users/user1/eclipse-workspace/logback-learning/log-file.%d{yyyy-MM-dd_HH}.log
</fileNamePattern>
<maxHistory>240</maxHistory>
</rollingPolicy>
<encoder>
<pattern>%d{yyyy-MM-dd HH:mm:ss.SSS} %thread %-5level
%logger{0} %L - %msg%n </pattern>
</encoder>
</appender>
<appender name="ASYNC-STDOUT"
class="ch.qos.logback.classic.AsyncAppender">
<queueSize>0</queueSize>
<discardingThreshold>1</discardingThreshold>
<neverBlock>true</neverBlock>
<appender-ref ref="STDOUT" />
</appender>
<root level="INFO">
<appender-ref ref="ASYNC-STDOUT" />
<appender-ref ref="FILE" />
</root>
</configuration>
当我运行它时;我看到以下线程转储(片段(:
"logback-1" #13 daemon prio=5 os_prio=31 tid=0x00007fd01d93a800 nid=0xa603 waiting on condition [0x00007000071c7000]
java.lang.Thread.State: TIMED_WAITING (parking)
at sun.misc.Unsafe.park(Native Method)
- parking to wait for <0x0000000797600730> (a java.util.concurrent.locks.AbstractQueuedSynchronizer$ConditionObject)
at java.util.concurrent.locks.LockSupport.parkNanos(LockSupport.java:215)
at java.util.concurrent.locks.AbstractQueuedSynchronizer$ConditionObject.awaitNanos(AbstractQueuedSynchronizer.java:2078)
at java.util.concurrent.ScheduledThreadPoolExecutor$DelayedWorkQueue.take(ScheduledThreadPoolExecutor.java:1093)
at java.util.concurrent.ScheduledThreadPoolExecutor$DelayedWorkQueue.take(ScheduledThreadPoolExecutor.java:809)
at java.util.concurrent.ThreadPoolExecutor.getTask(ThreadPoolExecutor.java:1074)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1134)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624)
at java.lang.Thread.run(Thread.java:748)
"main" #1 prio=5 os_prio=31 tid=0x00007fd01d00f800 nid=0x1803 runnable [0x0000700005b85000]
java.lang.Thread.State: RUNNABLE
at com.example.Slf4jApp1.<clinit>(Slf4jApp1.java:13)
我调试了它,并在第一条语句上找到了断点:
private static final Logger LOGGER = LoggerFactory.getLogger(Slf4jApp1.class);
我不明白logback-1
线程是如何产生的,它是不是只是在pom.xml中有maven依赖关系而创建的?另外,我还没有给出任何特定的指令/JVM OPTS,那么为什么会产生新的线程呢?
IntelliJ IDEA中的字段断点就是这样工作的。Put LOGGER=LoggerFactory.getLogger(Slf4jApp1.class(;和一个静态块中的断点,并查看是否没有logback线程。