apache2日志定制

由于工作需要,需要对访问记录进行过滤,所以需要对日志生成的格式进行定制化。

认识日志格式

制日志文件的格式涉及到两个指令,即LogFormat指令和CustomLog指令,默认httpd.conf文件提供了关于这两个指令的几个示例。

1
2
LogFormat "%h %l %u %t \"%r\" %>s %b \"%{Referer}i\" \"%{User-Agent}i\"" combined
LogFormat "%h %l %u %t \"%r\" %>s %b" common

科普一下。

  • 通用日志格式(Common Log Format)
    这是一个典型的记录格式:
    1
    2
    LogFormat "%h %l %u %t \"%r\" %>s %b" common
    CustomLog logs/access_log common

它定义了一种特定的记录格式字符串,并给它起了个别名叫common ,其中的%指示服务器用某种信息替换,其他字符则不作替换。引号(“)必须加反斜杠转义,以避免被解释为字符串的结束。格式字符串还可以包含特殊的控制符,如换行符\n 、制表符\t
CustomLog指令建立一个使用指定别名的新日志文件,除非其文件名是以斜杠开头的绝对路径,否则其路径就是相对于ServerRoot的相对路径。

上述配置是一种被称为通用日志格式(CLF)的记录格式,它被许多不同的Web服务器所采用,并被许多日志分析程序所识别,它产生的记录形如:

1
127.0.0.1 - - [30/Aug/2017:10:01:57 +0800] "GET /phpinfo.php HTTP/1.1" 200 58518

部分说明如下:

1
2
3
4
5
6
7
127.0.0.1 (%h) #发送请求到服务器的客户的IP地址
- (%l) #由客户端identd进程判断的RFC1413身份(identity),输出中的符号"-"表示此处的信息无效。(不推荐使用)
- (%u) #HTTP认证系统得到的访问该网页的客户标识(userid),环境变量REMOTE_USER会被设为该值并提供给CGI脚本(一般为无意义项)
[30/Aug/2017:10:01:57 +0800] (%t) #服务器完成请求处理时的时间 [日/月/年:时:分:秒 时区]
\"%r\" #客户端发出的包含许多有用信息的请求行
200 (%>s) #服务器返回给客户端的状态码
58518 (%b) #不包括相应头的字节数,如果想要设置记录为0,则设置为%B

  • 组合日志格式(Combined Log Format)

另一种常用的记录格式是组合日志格式,形式如下:

1
2
LogFormat "%h %l %u %t \"%r\" %>s %b \"%{Referer}i\" \"%{User-agent}i\"" combined
CustomLog log/access_log combined

这种格式与通用日志格式类似,但是多了两个 \"%{header}i\" 项,其中的header可以是任何请求头。这种格式的记录形如:

1
192.168.2.101 - - [31/Aug/2017:14:32:39 +1200] "GET /demo.php?dir=C%3A\\phpStudy\\WWW\\&Submit=%E6%A3%80%E6%B5%8B HTTP/1.1" 200 70971 "-" "Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:52.0) Gecko/20100101 Firefox/52.0"

其中,多出来的项是:

1
2
(\"%{Referer}i\") #因为我这里是本地做的测试,所以Referer信息没有显示。此项指明了该请求是被从哪个网页提交过来的,这个网页应该包含有/demo.php或者其连接。
"Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:52.0) Gecko/20100101 Firefox/52.0" (\"%{User-agent}i\") #"User-Agent"请求头。此项是客户端提供的浏览器识别信息。

定制日志格式

首先从命令开始

1
2
可以简单地在配置文件中用多个CustomLog指令来建立多文件访问日志
CustomLog log/demo/demo.log demo #文件夹提前建立

一般获取得信息只需要是远程访问主机IP(%h),访问时间(%t),请求行,状态码(%>s),浏览器信息(\”%{User-agent}i\”)
而特殊的

1
2
3
4
5
6
7
8
9
10
11
12
13
14
只是记录404的状态,
LogFormat %404{Referer}i BrokenLinks
使用env
SetEnvIfNoCase 当满足某个条件时,为变量赋值,一般结合其他指令使用。如:
1。SetEnvIf Request_URI "/logo(.)+" local_ref=0
Allow from env=local_ref 当local_ref有值时,可以访问。
2。SetEnvIfNoCase Request_URI .js$ useless-file
CustomLog logs/demo/demo.log demo env=!useless-file
当满足条件时才记录日志。
使用rotatelogs进行分隔
CustomLog "|bin/rotatelogs.exe -l logs/demo/demo_%Y%m%d.log 86400" demo
个人再windows下使用rotatelogs.exe会跳出一个窗口

弄了下,没看到想要的效果,有时间再更新下

筛选

弄到最后,就想着用python直接提取需要的数据行就行。
demo:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
#-*- coding: UTF-8 -*-
import sys
def readlog(keywords,outputfile,logpath):
file = open(logpath,"r")
filename = open(outputfile,"a")
for dirr in file:
if keywords in dirr:
filename.write(dirr+"\n")
if __name__ == '__main__':
if len(sys.argv) < 4:
print('Usage:\n\t%s keywords outputfile logpath' % sys.argv[0])
else:
keywords = sys.argv[1].strip()
outputfile = sys.argv[2].strip()
logpath = sys.argv[3].strip()
readlog(keywords,outputfile,logpath)

当然,筛选的方法多种多样。

参考:
Apache的日志文件
Apache日志配置

!坚持技术分享,您的支持将鼓励我继续创作!