2014-01-16 97 views
6

我試圖從SLF4J FAQ的簡單的例子:爲什麼異常堆棧跟蹤沒有登錄?

package com.aed.tests.logging; 
import org.slf4j.LoggerFactory; 

public class TestLogging 
{ 

    public TestLogging() 
    { 
     // TODO Auto-generated constructor stub 
    } 

    /** 
    * @param args 
    */ 
    public static void main(String[] args) 
    { 
     String s = "Hello world"; 
     try 
     { 
      Integer i = Integer.valueOf(s); 
     } 
     catch(NumberFormatException e) 
     { 
      LoggerFactory.getLogger("simplelogger").error("Failed to format {}", s, e); 
      LoggerFactory.getLogger("simplelogger").error("Without parametrized string", e); 

     } 
    } 
} 

這裏是輸出:

15:33:51,248000000 [SEVERE]simplelogger: Failed to format Hello world 
15:33:51,275000000 [SEVERE]simplelogger: Without parametrized string 

我使用的java.util.logging作爲日誌記錄實現,具有以下logging.properties

# Properties file which configures the operation of the JDK 
# logging facility. 

# The system will look for this config file, first using 
# a System property specified at startup: 
# 
# >java -Djava.util.logging.config.file=myLoggingConfigFilePath 
# 
# If this property is not specified, then the config file is 
# retrieved from its default location at: 
# 
# JDK_HOME/jre/lib/logging.properties 

# Global logging properties. 
# ------------------------------------------ 
# The set of handlers to be loaded upon startup. 
# Comma-separated list of class names. 
# (? LogManager docs say no comma here, but JDK example has comma.) 
handlers=java.util.logging.ConsoleHandler 

# Default global logging level. 
# Loggers and Handlers may override this level 
.level=ALL 

# Loggers 
# ------------------------------------------ 
# Loggers are usually attached to packages. 
# Here, the level for each package is specified. 
# The global level is used by default, so levels 
# specified here simply act as an override. 
# myapp.ui.level=ALL 
# myapp.business.level=CONFIG 
# myapp.data.level=SEVERE 

# Handlers 
# ----------------------------------------- 

# --- ConsoleHandler --- 
# Override of global logging level 
java.util.logging.ConsoleHandler.level=ALL 
java.util.logging.ConsoleHandler.formatter=java.util.logging.SimpleFormatter 
# HH:MM:ss,nanosec 
java.util.logging.SimpleFormatter.format=%1$tT,%1$tN [%4$s]%3$s: %5$s %n 

我希望看到異常的堆棧跟蹤。我在配置中丟失了什麼嗎?以SLF4J或jdk日誌記錄方式啓動異常痕跡?

編輯下面的「標記爲重複」。 我的問題不是「如何打印堆棧跟蹤」,而是如何使用SLF4J本身的作業打印出堆棧跟蹤的例子,我還沒有打印出堆棧跟蹤。正如我所說,我已經使用log4j作爲實現而不是java.util.logging打印出堆棧跟蹤。所以這確實是java.util.logging配置錯誤的問題,當我發現時我給出了答案。

+0

與log4j的作爲實現剛纔試了,我的確得到了堆跟蹤。那麼JDK日誌記錄是否不能記錄堆棧跟蹤? – remi

回答

7

確實是爲日誌記錄正確配置格式化程序的問題。

作爲manual says,throwable是方法格式的第6個參數。因此,我增加%6$s到我的格式logging.properties:

java.util.logging.SimpleFormatter.format=%1$tT,%1$tN [%4$s]%3$s: %5$s %6$s %n 

這裏是輸出,顯示堆棧跟蹤:

17:29:33,314000000 [SEVERE]simplelogger: Failed to format Hello world 
java.lang.NumberFormatException: For input string: "Hello world" 
    at java.lang.NumberFormatException.forInputString(NumberFormatException.java:65) 
    at java.lang.Integer.parseInt(Integer.java:492) 
    at java.lang.Integer.valueOf(Integer.java:582) 
    at com.aed.tests.logging.TestLogging.main(TestLogging.java:15) 

17:29:33,344000000 [SEVERE]simplelogger: Without parametrized string 
java.lang.NumberFormatException: For input string: "Hello world" 
    at java.lang.NumberFormatException.forInputString(NumberFormatException.java:65) 
    at java.lang.Integer.parseInt(Integer.java:492) 
    at java.lang.Integer.valueOf(Integer.java:582) 
    at com.aed.tests.logging.TestLogging.main(TestLogging.java:15)