温馨提示×

如何轮转debian golang日志

小樊
46
2026-09-13 01:56:07
栏目: 编程语言

在 Debian 上运行用 Go (Golang) 写的服务时,“日志轮转(log rotation)”通常不是在 Go 代码里硬写,而是交给系统工具处理。下面是几种常见、推荐的做法。


一、使用 logrotate(最推荐,Debian 标配)

Debian 自带 logrotate,几乎适合所有场景。

1. 假设你的 Go 程序日志写在:

/var/log/myapp/app.log

2. 创建 logrotate 配置

sudo vim /etc/logrotate.d/myapp

示例配置:

/var/log/myapp/*.log {
    daily
    missingok
    rotate 14
    compress
    delaycompress
    notifempty
    copytruncate
}

关键参数说明

  • copytruncate非常重要,适合不支持信号重开日志的 Go 程序
  • daily / weekly:轮转频率
  • rotate 14:保留 14 份
  • compress:压缩旧日志

3. 测试配置

sudo logrotate -d /etc/logrotate.d/myapp
sudo logrotate -f /etc/logrotate.d/myapp

✅ 优点:简单、稳定、无需改代码
❌ 缺点:依赖 copytruncate(有极少量日志丢失风险)


二、Go 程序自身支持 SIGHUP(更优雅)

如果你的 Go 程序能监听信号重新打开日志文件

Go 示例(简化)

sigChan := make(chan os.Signal, 1)
signal.Notify(sigChan, syscall.SIGHUP)

go func() {
    for range sigChan {
        logFile.Close()
        logFile, _ = os.OpenFile("/var/log/myapp/app.log", os.O_APPEND|os.O_CREATE|os.O_WRONLY, 0644)
        log.SetOutput(logFile)
    }
}()

logrotate 配置

/var/log/myapp/*.log {
    daily
    rotate 14
    compress
    postrotate
        systemctl kill -s HUP myapp.service
    endscript
}

✅ 优点:无日志丢失
❌ 缺点:需要改代码


三、使用 Go 日志库(自动轮转)

如果不想依赖系统工具,可以用 Go 库:

1. lumberjack(最流行)

import "gopkg.in/natefinch/lumberjack.v2"

log.SetOutput(&lumberjack.Logger{
    Filename:   "/var/log/myapp/app.log",
    MaxSize:    10, // MB
    MaxBackups: 14,
    MaxAge:     28, // days
    Compress:   true,
})

✅ 优点:代码可控
❌ 缺点:日志命名不是 app.log.1 标准格式


四、systemd 方式(Journal + 文件)

如果日志直接输出到 stdout:

# /etc/systemd/system/myapp.service
[Service]
ExecStart=/opt/myapp/myapp
StandardOutput=journal

查看日志:

journalctl -u myapp

systemd 会自动轮转 journal。


五、推荐方案总结

场景 推荐
不想改代码 logrotate + copytruncate
可接受改代码 logrotate + SIGHUP
容器 / 云原生 stdout + 外部采集
纯 Go 项目 lumberjack

如果你愿意,可以告诉我:

  • 你的 Go 程序怎么写日志(stdout / 文件)
  • 是否用 systemd
  • Debian 版本

我可以给你一份可直接用的配置

0