日誌是生產環境排查問題的生命線。濫用 System.out.println、e.printStackTrace() 缺乏級別、格式、輸出控制,必須遷移至專業日誌框架。
Logger 發起請求,關聯名稱 (通常為類名)、級別Formatter/PatternLayout 裝飾元數據 (時間、線程、類名等)Handler/Appender 輸出至控制台、文件、資料庫、郵件、JMS 等| 框架 | 定位 | 特點 |
|---|---|---|
| JUL (java.util.logging) | JDK 內置 | 零依賴、功能弱、配置繁瑣 |
| Log4j 1.x | 社區經典 | 停止維護、漏洞風險 |
| Logback | Log4j 繼任者 | 原生實現 SLF4J、性能優、配置靈活 |
| Log4j 2.x | 新一代 | 異步日誌、GC-free、插件化 |
推薦:SLF4J API + Logback 實現,或 Log4j 2 API + 實現。
private static final Logger LOG = LoggerFactory.getLogger(MyClass.class);
if (LOG.isDebugEnabled()) {
LOG.debug("User {} logged in from IP {}", userId, ip); // 參數化避免字符串拼接開銷
}
{} 佔位符,僅在啟用級別時構建字符串MDC.put("traceId", UUID.randomUUID().toString());
MDC.put("userId", userId);
LOG.info("Processing order"); // 日誌自動包含 traceId、userId
MDC.clear(); // 線程池場景必須清理
配合 %X{traceId} 模式實現全鏈路追蹤。
[user=123] [order=456] Payment succeeded 便於正則/工具提取input { file { path => ["/var/log/*.log"] } }
filter { grok { match => { message => "%{COMBINEDAPACHELOG}" } } }
output { elasticsearch { hosts => ["localhost:9200"] } }
Grok 正則提取結構化字段 (clientip、method、status 等)。
倒排索引支撐全文搜索、聚合分析。
Logstash 輸出切換:
output { gelf { host => "127.0.0.1" } } # Graylog2
output { elasticsearch { hosts => ["localhost:9200"] } } # Kibana
專業日誌體系 = 規範 API 使用 (SLF4J/Logback) + 結構化輸出 (JSON/GELF) + 集中聚合 (Logstash+ES) + 可視化分析 (Kibana)。從代碼層面落地規範,到基礎設施層面構建可觀測性平台。