🐧 Linux LogRotate 日誌自動輪替與清理教學(含 systemd / cron 實作)
維運環境中,日誌若不規劃,磁碟容易被塞滿、分析也變困難。LogRotate 可針對大小或時間自動分檔、壓縮與清理,並在輪替後重載服務。本文提供 一步一步 的實作範例,並解釋 systemd timer 與 cron.daily 兩種啟動方式,最後附上常見錯誤排查清單與安全最佳實務。
📑 目錄
- 一、核心概念與檔案佈局
- 二、全域設定:
/etc/logrotate.conf - 三、每服務配置:
/etc/logrotate.d/範例 - 四、排程觸發:
systemd timervscron.daily - 五、驗證與手動輪替
- 六、常見錯誤與排查
- 七、安全與最佳實務(Hardening)
- 八、實用 Recipes(可直接套用)
- 🔗 延伸閱讀
一、核心概念與檔案佈局
- 主設定檔:
/etc/logrotate.conf(放全域規則與 include 指令)。 - 服務分檔:
/etc/logrotate.d/*(各服務各寫一份)。 - 運作模式:依 時間(daily/weekly/monthly) 或 大小(size) 輪替;可選擇 compress/delaycompress、rotate N、missingok、notifempty 等。
- 輪替後動作:
postrotate/endscript內呼叫systemctl reload或kill -HUP讓服務重載。
二、全域設定:/etc/logrotate.conf
# /etc/logrotate.conf
# 全域預設(可被 /etc/logrotate.d/* 覆寫)
weekly # 每週輪替
rotate 4 # 保留 4 份歷史檔
create # 建立新檔,沿用預設權限(可於個別檔案強化)
dateext # 使用日期作為副檔名
compress # 壓縮舊檔(搭配 delaycompress 更安全)
include /etc/logrotate.d
# 針對 wtmp/btmp 的示例(系統登入紀錄)
/var/log/wtmp {
monthly
rotate 12
create 0664 root utmp
missingok
}
/var/log/btmp {
monthly
rotate 12
create 0600 root utmp
missingok
}
三、每服務配置:/etc/logrotate.d/ 範例
範例 A:Nginx 存取/錯誤日誌
# /etc/logrotate.d/nginx
/var/log/nginx/*.log {
weekly
rotate 8
size 50M
missingok
notifempty
compress
delaycompress
dateext
create 0640 www-data adm
sharedscripts
postrotate
# 以重載方式讓 Nginx 重新打開檔案句柄
[ -s /run/nginx.pid ] && systemctl reload nginx.service
endscript
}
範例 B:應用程式單一檔案(支援 copytruncate)
# /var/log/myapp/app.log 若程式無法 HUP 重載,可用 copytruncate
/var/log/myapp/app.log {
daily
rotate 14
size 10M
missingok
notifempty
compress
delaycompress
dateext
copytruncate # 先複製舊檔再 truncate 原檔,避免重啟服務
}
範例 C:多檔規則 + 權限強化
# /etc/logrotate.d/myapps
/var/log/myapps/*.log {
weekly
rotate 6
missingok
notifempty
compress
dateext
su root adm # 以 logrotate 的 su 機制維持權限
create 0640 root adm
}
四、排程觸發:systemd timer vs cron.daily
大多數新版發行版已使用 logrotate.timer;舊版則由 /etc/cron.daily/logrotate 觸發。
# ✅ 建議:啟用 systemd timer(具可觀察性、易管理)
sudo systemctl enable --now logrotate.timer
systemctl status logrotate.timer
systemctl list-timers | grep logrotate
# 若使用傳統 cron(依發行版預設)
ls -l /etc/cron.daily/logrotate
sudo run-parts /etc/cron.daily # 立即觸發每日工作(測試用)
何者優先? 若同時存在,請擇一;避免「timer + cron」雙重觸發導致並行輪替。
五、驗證與手動輪替
# 乾跑(不實作),檢查設定是否正確
sudo logrotate -d /etc/logrotate.conf
# 強制輪替(測試實作)
sudo logrotate -f /etc/logrotate.conf
# 觀察結果與壓縮檔
ls -lh /var/log/nginx/
ls -lh /var/log/myapp/
六、常見錯誤與排查
- Permission denied/無法建立新檔:為規則加入
create 0640 user group或使用su子句。 - 輪替後服務仍寫入舊檔:多半是服務未重載;在
postrotate呼叫systemctl reload或使用copytruncate。 - 並行輪替衝突:避免
logrotate.timer與cron.daily同時啟用;關閉其一。 - 壓縮檔未出現:檢查是否設了
delaycompress(壓縮會延後到下一次輪替)。 - 容量未下降:輪替後未重載的服務仍持有檔案描述符;
lsof | grep deleted可查已刪但被佔用的檔案。
七、安全與最佳實務(Hardening)
- 最小化權限:重要日誌使用
create 0600 root adm,避免一般使用者可讀。 - 避免覆寫:優先使用
create或copytruncate,不要用手動> file方式清空。 - 保留週期依合規:依內控/法規需求設定
rotate N(例如安全稽核要求保留 6–12 個月)。 - 與集中化搭配:關鍵日誌建議輸出到集中式(rsyslog/Logstash),輪替僅做本機控重。
八、實用 Recipes(可直接套用)
R1:高流量網站的「時間 + 大小」雙條件
/var/log/nginx/*.log {
daily
size 100M
rotate 14
missingok
compress
delaycompress
dateext
create 0640 www-data adm
sharedscripts
postrotate
systemctl reload nginx.service
endscript
}
R2:journald 清理(配合 LogRotate 的容量治理)
# 設定 journald 儲存上限(/etc/systemd/journald.conf)
SystemMaxUse=2G
SystemMaxFileSize=200M
RuntimeMaxUse=512M
# 立即清理舊日誌(保留 14 天內)
sudo journalctl --vacuum-time=14d
# 或依容量清理,保留最近 1G
sudo journalctl --vacuum-size=1G
R3:自訂任務以 timer 週期掃除大型暫存檔
# /etc/systemd/system/tmp-clean.service
[Unit]
Description=Scheduled temp cleanup
[Service]
Type=oneshot
ExecStart=/usr/bin/find /var/tmp -type f -mtime +7 -delete
# /etc/systemd/system/tmp-clean.timer
[Unit]
Description=Run temp cleanup daily
[Timer]
OnCalendar=daily
RandomizedDelaySec=120
Persistent=true
[Install]
WantedBy=timers.target
# 啟用
sudo systemctl enable --now tmp-clean.timer
systemctl list-timers | grep tmp-clean
🔗 延伸閱讀
- Linux 集中式日誌 rsyslog:集中收集與分析
- Proxy/GoAccess:流量日誌視覺化分析
- Firewall × Fail2Ban × systemd:惡意 IP 防護
- 自動化日誌:GoAccess + Fail2Ban 進階
🧭 行動清單
✅ 啟用 logrotate.timer(或確認 cron.daily)並擇一 ✅ 為 Nginx / 應用服務增設 /etc/logrotate.d/ 個別規則 ✅ 以 logrotate -d 與 -f 驗證流程;搭配 journalctl 觀察 ✅ 對安全性高的日誌採 create 0600 與 su 權限控管 ✅ 搭配 rsyslog / GoAccess 做集中化與可視化
— WWFandy・主題筆記
沒有留言: