一、为什么需要日志轮转
数据库运行过程中会产生大量日志文件,如果不加以管理,这些文件很快就会占满磁盘空间。想象一下,你正在度假,突然收到服务器磁盘告警,不得不紧急处理——这种场景谁都不想遇到。PostgreSQL 默认会将日志输出到单个文件中,随着时间推移,这个文件可能增长到几个 GB 甚至更大,不仅占用空间,还会影响日志查阅效率。
日志轮转(Log Rotation)就是解决这个问题的标准方案。它通过定期归档、压缩旧日志,并创建新日志文件,确保日志总量可控。在 Linux 系统中,logrotate 是完成这项任务的经典工具,它支持按时间、按大小触发轮转,还能在轮转后执行自定义命令(比如通知 PostgreSQL 重新打开日志文件)。
二、logrotate 基础配置
我们先来看一个最简单的 logrotate 配置示例(技术栈:Linux + PostgreSQL):
# /etc/logrotate.d/postgresql
/var/log/postgresql/postgresql.log {
daily # 每天轮转一次
missingok # 如果日志文件不存在也不报错
rotate 7 # 保留最近7天的日志
compress # 压缩旧日志
delaycompress # 下一次轮转时再压缩
notifempty # 如果日志为空则不轮转
sharedscripts # 所有日志处理完再执行脚本
postrotate # 轮转后执行的命令
/usr/bin/pg_ctl reload -D /var/lib/postgresql/data >/dev/null
endscript
}
关键参数解析:
daily/weekly/monthly:轮转周期,也可用size(例如size 100M)rotate N:保留的历史日志数量compress:用 gzip 压缩旧日志(生成 .gz 文件)postrotate:这里通过pg_ctl reload让 PostgreSQL 重新打开日志文件
三、分离错误日志与查询日志
实际生产中,我们通常希望将错误日志(error log)和查询日志(query log)分开管理。PostgreSQL 通过 logging_collector 和 log_destination 参数控制日志行为。修改 postgresql.conf:
# 启用日志收集器
logging_collector = on
# 日志输出到文件
log_destination = 'stderr'
# 错误日志路径
log_directory = '/var/log/postgresql'
log_filename = 'postgresql-error.log'
# 开启查询日志(慎用,对性能有影响)
log_statement = 'all'
# 查询日志单独存放
log_line_prefix = '%t [%p] ' # 时间戳和进程ID
对应的 logrotate 配置需调整为:
# /etc/logrotate.d/postgresql
/var/log/postgresql/postgresql-error.log {
daily
rotate 30 # 错误日志保留更久
compress
postrotate
/usr/bin/pg_ctl reload -D /var/lib/postgresql/data
endscript
}
/var/log/postgresql/postgresql-query.log {
weekly # 查询日志轮转频率较低
rotate 4 # 保留4周
size 100M # 或达到100MB时轮转
compress
delaycompress
postrotate
/usr/bin/pg_ctl reload -D /var/lib/postgresql/data
endscript
}
四、高级技巧与注意事项
1. 手动触发轮转测试
不要等到自动轮转时才发现配置错误,可以手动运行以下命令测试:
logrotate -vf /etc/logrotate.d/postgresql
-v 显示详细过程,-f 强制立即执行。
2. 处理权限问题
如果 PostgreSQL 以非 root 用户运行,需确保日志目录权限正确:
chown postgres:postgres /var/log/postgresql
chmod 750 /var/log/postgresql
3. 避免日志丢失
在 postrotate 脚本中,pg_ctl reload 是关键。如果忘记这一步,PostgreSQL 会继续向已轮转的旧文件写入日志,导致新日志文件为空。
4. 性能权衡
全量查询日志(log_statement = 'all')会显著增加 I/O 负载,建议仅在调试时开启,生产环境可改为 'ddl' 或 'mod'。
五、应用场景与总结
典型场景:
- 合规性要求保留一定期限的数据库日志
- 磁盘空间有限的中小型数据库实例
- 需要定期分析错误日志的运维监控系统
优点:
- 自动化管理,避免手动清理
- 压缩旧日志节省空间
- 与 Linux 生态无缝集成
缺点:
- 需要正确配置
postrotate脚本 - 频繁轮转可能增加 CPU 负载(压缩操作)
最终建议:
对于高负载生产环境,可考虑将日志发送到 ELK 或 Prometheus 等集中式日志系统,但 logrotate 仍是轻量级方案的优选。配置完成后,建议通过 cron 日志检查轮转是否正常执行,例如:
grep logrotate /var/log/cron.log
评论