Commons Logging (JCL) 作為日誌門面,Log4j 作為具體實現,兩者結合實現「代碼依賴門面、運行時綁定實現」的解耦架構。本文詳解整合原理、配置模板與最佳實踐。
commons-logging.properties 指定實現類org.apache.commons.logging.Logjava.util.loggingSimpleLog(功能極弱)log4j.jar 放入 classpath,JCL 即自動使用 Log4j,無需額外配置。import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
public class UserService {
// 靜態實例,避免重複創建
private static final Log log = LogFactory.getLog(UserService.class);
public void register(User user) {
log.debug("開始註冊用戶: " + user.getName());
// ... 業務邏輯
log.info("用戶註冊成功, ID: " + user.getId());
if (user.getEmail() == null) {
log.warn("用戶未填寫郵箱");
}
}
}
關鍵點:
LogFactory.getLog(當前類.class) 而非 getLog(this.getClass())(靜態上下文無 this)。DEBUG < INFO < WARN < ERROR < FATAL。### 根記錄器:級別 + 輸出目的地(多個用逗號分隔)
log4j.rootLogger = DEBUG, CONSOLE, FILE, ROLLING_FILE
### 控制台輸出
log4j.appender.CONSOLE = org.apache.log4j.ConsoleAppender
log4j.appender.CONSOLE.Target = System.out
log4j.appender.CONSOLE.layout = org.apache.log4j.PatternLayout
log4j.appender.CONSOLE.layout.ConversionPattern = [%d{yyyy-MM-dd HH:mm:ss}] [%p] [%c] - %m%n
### 固定文件輸出
log4j.appender.FILE = org.apache.log4j.FileAppender
log4j.appender.FILE.File = logs/app.log
log4j.appender.FILE.Append = true
log4j.appender.FILE.layout = org.apache.log4j.PatternLayout
log4j.appender.FILE.layout.ConversionPattern = [%d] [%p] [%c] - %m%n
### 滾動文件(按大小/備份數)
log4j.appender.ROLLING_FILE = org.apache.log4j.RollingFileAppender
log4j.appender.ROLLING_FILE.File = logs/app-rolling.log
log4j.appender.ROLLING_FILE.MaxFileSize = 10MB
log4j.appender.ROLLING_FILE.MaxBackupIndex = 10
log4j.appender.ROLLING_FILE.layout = org.apache.log4j.PatternLayout
log4j.appender.ROLLING_FILE.layout.ConversionPattern = [%d] [%p] [%c] - %m%n
### 按天滾動(DailyRollingFileAppender)
log4j.appender.DAILY = org.apache.log4j.DailyRollingFileAppender
log4j.appender.DAILY.File = logs/app-daily.log
log4j.appender.DAILY.DatePattern = '.'yyyy-MM-dd
log4j.appender.DAILY.layout = org.apache.log4j.PatternLayout
log4j.appender.DAILY.layout.ConversionPattern = [%d] [%p] [%c] - %m%n
### 郵件通知(僅 ERROR/FATAL)
log4j.appender.MAIL = org.apache.log4j.net.SMTPAppender
log4j.appender.MAIL.Threshold = ERROR
log4j.appender.MAIL.BufferSize = 10
log4j.appender.MAIL.From = app@company.com
log4j.appender.MAIL.SMTPHost = smtp.company.com
log4j.appender.MAIL.Subject = 【生產告警】%c - %m
log4j.appender.MAIL.To = ops@company.com
log4j.appender.MAIL.layout = org.apache.log4j.PatternLayout
log4j.appender.MAIL.layout.ConversionPattern = [%d] [%p] [%c] - %m%n
rootLogger 級別為全局閾值(如 DEBUG 允許所有級別通過)。Appender 可設 Threshold 進一步過濾(如控制台 DEBUG、文件 INFO、郵件 ERROR)。避免相對路徑(默認指向 Tomcat bin/ 目錄),建議用絕對路徑或相對 catalina.base:
log4j.appender.FILE.File = ${catalina.base}/logs/app.log
public final class Logs {
private static final Log LOG = LogFactory.getLog(Logs.class);
private Logs() {}
public static Log getLog() { return LOG; }
}
// 業務調用
Logs.getLog().info("業務開始");
Logs.getLog().error("業務異常", e);
集中管理日誌實例,便於統一級別控制與格式調整。