最新消息:

【分享】Logrotate + syslogd 日志轮换管理工具总结

应用服务 摘星怪 532浏览 0评论

Logrotate的介绍

logrotate是在规定时间到了之后才来进行日志文件的轮替,所以logrotate程序是挂在cron下面进行的,/etc/cron.daily/logrotate记录了每天要进行的日志文件轮替行为。

logrotate的配置文件:
/etc/logrotate.conf
/etc/logrotate.d/

logrotate.conf 是主要的参数文件,logrotate.d 是一个目录,该目录里面的所有数据都会被主动读入/etc/logrotate.conf 当中来进行。

另外,在/etc/logrotate.d/ 里面的文件中,如果没有指定一些详细的设置,则以 /etc/logrotate.conf 的规定来指定为默认值。

显而易见,Logrotate是基于CRON来运行的,其脚本是「/etc/cron.daily/logrotate」:

#!/bin/sh

/usr/sbin/logrotate /etc/logrotate.conf
EXITVALUE=$?
if [ $EXITVALUE != 0 ]; then
    /usr/bin/logger -t logrotate "ALERT exited abnormally with [$EXITVALUE]"
fi
exit 0

实际运行时,Logrotate会调用配置文件「/etc/logrotate.conf」:

# see "man logrotate" for details
# rotate log files weekly
weekly

# keep 4 weeks worth of backlogs
rotate 4

# create new (empty) log files after rotating old ones
create

# uncomment this if you want your log files compressed
#compress

# RPM packages drop log rotation information into this directory
include /etc/logrotate.d

# no packages own wtmp -- we'll rotate them here
/var/log/wtmp {
    monthly
    minsize 1M
    create 0664 root utmp
    rotate 1
}

# system-specific logs may be also be configured here.

这里的设置可以理解为Logrotate的缺省值,当然了,可以我们在「/etc/logrotate.d」目录里放置自己的配置文件,用来覆盖Logrotate的缺省值。

Logrotate的演示

按天保存一周的Nginx日志压缩文件,配置文件为「/etc/logrotate.d/nginx」:

/usr/local/nginx/logs/*.log {
    daily
    dateext
    compress
    rotate 7
    sharedscripts
    postrotate
        kill -USR1 `cat /var/run/nginx.pid`
    endscript
}

如果你等不及CRON,可以通过如下命令来手动执行:

shell> logrotate -f /etc/logrotate.d/nginx

当然,正式执行前最好通过Debug选项来验证一下,这对调试也很重要:

shell> logrotate -d -f /etc/logrotate.d/nginx

BTW:类似的还有Verbose选项,这里就不多说了。

配置实例:

/var/log/messages {
    rotate 5
    weekly
    postrotate
        /sbin/killall -HUP syslogd
    endscript
}
 
"/var/log/httpd/access.log" /var/log/httpd/error.log {
    rotate 5
    mail www@my.org
    size 100k
    sharedscripts
    postrotate
        /sbin/killall -HUP httpd
    endscript
}
 
/var/log/news/* {
    monthly
    rotate 2
    olddir /var/log/news/old
    missingok
    postrotate
        kill -HUP ‘cat /var/run/inn.pid‘
    endscript
    nocompress
}

配置选项说明:

compress:通过gzip 压缩转储旧的日志
nocompress:不需要压缩时,用这个参数
copytruncate:用于还在打开中的日志文件,把当前日志备份并截断
nocopytruncate:备份日志文件但是不截断
create mode owner group:使用指定的文件模式创建新的日志文件
nocreate:不建立新的日志文件
delaycompress:和 compress 一起使用时,转储的日志文件到下一次转储时才压缩
nodelaycompress:覆盖 delaycompress 选项,转储同时压缩。
errors address:专储时的错误信息发送到指定的Email 地址
ifempty:即使是空文件也转储,这个是 logrotate 的缺省选项。
notifempty:如果是空文件的话,不转储
mail address:把转储的日志文件发送到指定的E-mail 地址
nomail:转储时不发送日志文件
olddir directory:转储后的日志文件放入指定的目录,必须和当前日志文件在同一个文件系统
noolddir:转储后的日志文件和当前日志文件放在同一个目录下
prerotate/endscript:在转储以前需要执行的命令可以放入这个对,这两个关键字必须单独成行
postrotate/endscript:在转储以后需要执行的命令可以放入这个对,这两个关键字必须单独成行
sharedscripts:所有的日志文件都轮转完毕后统一执行一次脚本
daily:指定转储周期为每天
weekly:指定转储周期为每周
monthly:指定转储周期为每月
rotate count:指定日志文件删除之前转储的次数,0 指没有备份,5 指保留5 个备份
size size:当日志文件到达指定的大小时才转储,Size 可以指定 bytes (缺省)以及KB (sizek)或者MB

Logrotate的疑问

问题:sharedscripts的作用是什么?

大家可能注意到了,我在前面Nginx的例子里声明日志文件的时候用了星号通配符,也就是说这里可能涉及多个日志文件,比如:access.log和error.log。说到这里大家或许就明白了,sharedscripts的作用是在所有的日志文件都轮转完毕后统一执行一次脚本。如果没有配置这条指令,那么每个日志文件轮转完毕后都会执行一次脚本。

问题:rotate和maxage的区别是什么?

它们都是用来控制保存多少日志文件的,区别在于rotate是以个数为单位的,而maxage是以天数为单位的。如果我们是以按天来轮转日志,那么二者的差别就不大了。

问题:为什么生成日志的时间是凌晨四五点?

前面我们说过,Logrotate是基于CRON运行的,所以这个时间是由CRON控制的,具体可以查询CRON的配置文件「/etc/crontab」,可以手动改成如23:59等时间执行:

SHELL=/bin/bash
PATH=/sbin:/bin:/usr/sbin:/usr/bin
MAILTO=root
HOME=/

# run-parts
01 * * * * root run-parts /etc/cron.hourly
59 23 * * * root run-parts /etc/cron.daily
22 4 * * 0 root run-parts /etc/cron.weekly
42 4 1 * * root run-parts /etc/cron.monthly

如果使用的是新版CentOS,那么配置文件为:/etc/anacrontab。

# cat /etc/anacrontab

里面有个

START_HOURS_RANGE=3-22    这个是开始时间

RANDOM_DELAY=45    这个是随机的延迟时间,表示最大45min.

还有个

1       5       cron.daily              nice run-parts /etc/cron.daily

第一个是Recurrence period  第二个是延迟时间,所以cron.daily会在3:22+(5,45)这个时间段执行,/etc/cron.daily是个文件夹

问题:如何告诉应用程序重新打开日志文件?

以Nginx为例,是通过postrotate指令发送USR1信号来通知Nginx重新打开日志文件的。但是其他的应用程序不一定遵循这样的约定,比如说MySQL是通过flush-logs来重新打开日志文件的。更有甚者,有些应用程序就压根没有提供类似的方法,此时如果想重新打开日志文件,就必须重启服务,但为了高可用性,这往往不能接受。还好Logrotate提供了一个名为copytruncate的指令,此方法采用的是先拷贝再清空的方式,整个过程中日志文件的操作句柄没有发生改变,所以不需要通知应用程序重新打开日志文件,但是需要注意的是,在拷贝和清空之间有一个时间差,所以可能会丢失部分日志数据。

BTW:MySQL本身在support-files目录已经包含了一个名为mysql-log-rotate的脚本,不过它比较简单,更详细的日志轮转详见「Rotating MySQL Slow Logs Safely」。

熟悉Apache的朋友可能会记得cronolog,不过Nginx并不支持它,有人通过mkfifo命令曲线救国,先给日志文件创建管道,再搭配cronolog轮转,虽然理论上没有问题,但效率上有折扣。另外,Debian/Ubuntu下有一个简化版工具savelog,有兴趣可以看看。

 syslogd  日志管理

软件包:sysklogd

配置文件:
/etc/syslog.conf  <—syslogd的主配置文件,存放的是syslogd记录日志的规则
/etc/sysconfig/syslog  <—保存一些启动的参数

字段的配置格式:设备.日志级别    动作

设备:
auth,     <—pam_pwd 产生的日志
authpriv  <—包括权限信息、用户登录的一些信息
cron    <—负责管理cron,at等日志信息的设备
daemon  <—xinetd 产生的日志 
kern    <—内核产生的日志
lpr    <—打印服务产生的日志 
mail    <—邮件产生日志
mark    <—syslogd内部功能,主要产生一个时间chuo
news    <—新闻组服务产生的日志
security (same as auth),   
syslog  <—syslogd本身产生的日志信息
user   <—用户程序产生的日志信息
uucp   <—文件拷贝服务产生的日志
local0 through local7.  <—程序自定义的日志设备

日志级别:

debug  <—产生的日志信息是最多一个
info    <—一般信息的日志,最常用的
notice    <—最具有重要性的普通条件的信息
warning <—预警的信息
warn (same as  warning) 
err    <—-阻止某个功能模块或者子系统不能正常工作的信息
error (same as err),
crit    <—-阻止整个系统或者整个软件不能正常的信息
alert   <—-需要马上修改的信息
emerg    <—-内核崩溃等严重错误
panic (same as emerg).
none    <—什么也不记录

日志的级别 从上往下级别从低到高涨,级别越低记录的信息越多,级别底的日志信息包括级别高的信息

#会记录 uucp,news两个设备产生的crit级别,以及包括crit更高级别的信息(alert,emerg)
uucp,news.crit                                          /var/log/spooler

#所以设备产生的info级别的信息,但除了mail,authpriv,cron的所有的记录以外,都记录在messages
*.info;mail.none;authpriv.none;cron.none                /var/log/messages

# authpriv设备所有级别的日志信息都记录到/var/log/secure
authpriv.*                                              /var/log/secure

# 用户自定义的设备
local7.*                                                /var/log/boot.log

#只包括mail设备产生的info级别的日志,但不包括任何级别的日志都记录到/var/log/mymail.log
mail.=info             /var/log/mymail.log

#把kern设备产生的info级别,以及包括info级别以上的级别(notice …. emerg)都记录,但除了err级别的日志
kern.info;kern.!err          /var/adm/kernel-info

例子:
vim /etc/ssh/sshd_config    

#SyslogFacility AUTHPRIV
SyslogFacility LOCAL6

vim /etc/syslog.conf  《--添加以下一行
local6.*                                                /var/log/mysshd.log

重启两个服务:
service syslog restart
service sshd restart

动作字段:

/filename.log  <—常规的日志文件
username    <—用户名,例如root,那么日志就会现是在root登录的所有终端,多个用户名用逗号分隔
terminal   《--例如写成 /dev/tty2  <—
@hostname   <—主机名字,把日志发送到远程的日志服务器

日志测试命令:
[root@dns ~]# logger -t “test_log” “this is log content! ”  《--通常用在shell脚本
[root@dns ~]# cat /var/log/messages
Nov 30 13:07:54 dns test_log: this is log content! 
日期       主机名 日志的标题    日志的内容

远程日志服务:
# vim /etc/sysconfig/syslog

服务端的配置:
-m 是够开启mark日志信息 ,-m 0 就是关闭这个功能, -m 120 就是每隔120分钟就产生一个时间信息
-r 是否允许接受远程发送过来的日志信息
-x 是否把IP转换成域名,-x不解析IP地址

启用接收远程发送过来的日志:
SYSLOGD_OPTIONS=”-r -m 0″

shell> service syslog restart

日志客户端的配置:
# vim /etc/syslog.conf
*.*             @dns.upl.com     《---把客户端的所有设备(除了mark外)的所有级别的日志都发送到dns.upl.com的远程服务器上

# vim /etc/hosts
10.1.1.20        dns.upl.com

# service syslog restart    

转载请注明:架构迷 » 【分享】Logrotate + syslogd 日志轮换管理工具总结

发表我的评论
取消评论

表情

Hi,您需要填写昵称和邮箱!

  • 昵称 (必填)
  • 邮箱 (必填)
  • 网址