Python 分析Nginx访问日志并保存到MySQL数据库实例
程序员文章站
2022-10-06 15:52:42
使用python 分析nginx access 日志,根据nginx日志格式进行分割并存入mysql数据库。一、nginx access日志格式如下:复制代码 代码如下:$...
使用python 分析nginx access 日志,根据nginx日志格式进行分割并存入mysql数据库。
一、nginx access日志格式如下:
复制代码 代码如下:
$remote_addr - $remote_user [$time_local] "$request" $status $body_bytes_sent "$http_referer" "$http_user_agent" "$http_x_forwarded_for"' #使用的是nginx默认日志格式
二、nginx access 日志内容如下:
复制代码 代码如下:
182.19.31.129 - - [2013-08-13t00:00:01-07:00] "get /css/anniversary.css http/1.1" 304 0 "http://www.chlinux.net/" "mozilla/5.0 (windows nt 6.1; wow64) applewebkit/537.36 (khtml, like gecko) chrome/28.0.1500.95 safari/537.36" "-"
三、下面是python 分析nginx日志的python代码:
复制代码 代码如下:
#!/usr/bin/env python
#coding:utf8
import os
import fileinput
import re
import sys
import mysqldb
#日志的位置
logfile=open("access_20130812.log")
#使用的nginx默认日志格式$remote_addr - $remote_user [$time_local] "$request" $status $body_bytes_sent "$http_referer" "$http_user_agent" "$http_x_forwarded_for"'
#日志分析正则表达式
#203.208.60.230
ipp = r"?p<ip>[\d.]*"
#以[开始,除[]以外的任意字符 防止匹配上下个[]项目(也可以使用非贪婪匹配*?) 不在中括号里的.可以匹配换行外的任意字符 *这样地重复是"贪婪的“ 表达式引擎会试着重复尽可能多的次数。#以]结束
#[21/jan/2011:15:04:41 +0800]
timep = r"""?p<time>\[[^\[\]]*\]"""
#以"开始, #除双引号以外的任意字符 防止匹配上下个""项目(也可以使用非贪婪匹配*?),#以"结束
#"get /entpshop.do?method=view&shop_id=391796 http/1.1"
#"get /entpshop.do?method=view&shop_id=391796 http/1.1"
requestp = r"""?p<request>\"[^\"]*\""""
statusp = r"?p<status>\d+"
bodybytessentp = r"?p<bodybytesent>\d+"
#以"开始, 除双引号以外的任意字符 防止匹配上下个""项目(也可以使用非贪婪匹配*?),#以"结束
#"http://test.myweb.com/myaction.do?method=view&mod_id=&id=1346"
referp = r"""?p<refer>\"[^\"]*\""""
#以"开始, 除双引号以外的任意字符 防止匹配上下个""项目(也可以使用非贪婪匹配*?),以"结束
#"mozilla/5.0 (compatible; googlebot/2.1; +http://www.google.com/bot.html)"'
useragentp = r"""?p<useragent>\"[^\"]*\""""
#以(开始, 除双引号以外的任意字符 防止匹配上下个()项目(也可以使用非贪婪匹配*?),以"结束
#(compatible; googlebot/2.1; +http://www.google.com/bot.html)"'
usersystems = re.compile(r'\([^\(\)]*\)')
#以"开始,除双引号以外的任意字符防止匹配上下个""项目(也可以使用非贪婪匹配*?),以"结束
userlius = re.compile(r'[^\)]*\"')
#原理:主要通过空格和-来区分各不同项目,各项目内部写各自的匹配表达式
nginxlogpattern = re.compile(r"(%s)\ -\ -\ (%s)\ (%s)\ (%s)\ (%s)\ (%s)\ (%s)" %(ipp, timep, requestp, statusp, bodybytessentp, referp, useragentp), re.verbose)
#数据库连接信息
conn=mysqldb.connect(host='192.168.1.22',user='test',passwd='pass',port=3306,db='python')
cur=conn.cursor()
sql = "insert into python.test values(%s,%s,%s,%s,%s,%s,%s,%s,%s)"
while true:
line = logfile.readline()
if not line:break
matchs = nginxlogpattern.match(line)
if matchs != none:
allgroup = matchs.groups()
ip = allgroup[0]
time = allgroup[1]
request = allgroup[2]
status = allgroup[3]
bodybytessent = allgroup[4]
refer = allgroup[5]
useragent = allgroup[6]
time = time.replace('t',' ')[1:-7]
if len(useragent) > 20:
userinfo = useragent.split(' ')
userkel = userinfo[0]
try:
usersystem = usersystems.findall(useragent)
usersystem = usersystem[0]
print usersystem
userliu = userlius.findall(useragent)
value = [ip,time,request,status,bodybytessent,refer,userkel,usersystem,userliu[1]]
conn.commit()
print value
except indexerror:
userinfo = useragent
value = [ip,time,request,status,bodybytessent,refer,userinfo,"",""]
else:
useraa = useragent
value = [ip,time,request,status,bodybytessent,refer,useraa,"",""]
try:
result = cur.execute(sql,value)
#conn.commit()
print result
except mysqldb.error,e:
print "mysql error %d: %s" % (e.args[0], e.args[1])
conn.commit()
conn.close()
#coding:utf8
import os
import fileinput
import re
import sys
import mysqldb
#日志的位置
logfile=open("access_20130812.log")
#使用的nginx默认日志格式$remote_addr - $remote_user [$time_local] "$request" $status $body_bytes_sent "$http_referer" "$http_user_agent" "$http_x_forwarded_for"'
#日志分析正则表达式
#203.208.60.230
ipp = r"?p<ip>[\d.]*"
#以[开始,除[]以外的任意字符 防止匹配上下个[]项目(也可以使用非贪婪匹配*?) 不在中括号里的.可以匹配换行外的任意字符 *这样地重复是"贪婪的“ 表达式引擎会试着重复尽可能多的次数。#以]结束
#[21/jan/2011:15:04:41 +0800]
timep = r"""?p<time>\[[^\[\]]*\]"""
#以"开始, #除双引号以外的任意字符 防止匹配上下个""项目(也可以使用非贪婪匹配*?),#以"结束
#"get /entpshop.do?method=view&shop_id=391796 http/1.1"
#"get /entpshop.do?method=view&shop_id=391796 http/1.1"
requestp = r"""?p<request>\"[^\"]*\""""
statusp = r"?p<status>\d+"
bodybytessentp = r"?p<bodybytesent>\d+"
#以"开始, 除双引号以外的任意字符 防止匹配上下个""项目(也可以使用非贪婪匹配*?),#以"结束
#"http://test.myweb.com/myaction.do?method=view&mod_id=&id=1346"
referp = r"""?p<refer>\"[^\"]*\""""
#以"开始, 除双引号以外的任意字符 防止匹配上下个""项目(也可以使用非贪婪匹配*?),以"结束
#"mozilla/5.0 (compatible; googlebot/2.1; +http://www.google.com/bot.html)"'
useragentp = r"""?p<useragent>\"[^\"]*\""""
#以(开始, 除双引号以外的任意字符 防止匹配上下个()项目(也可以使用非贪婪匹配*?),以"结束
#(compatible; googlebot/2.1; +http://www.google.com/bot.html)"'
usersystems = re.compile(r'\([^\(\)]*\)')
#以"开始,除双引号以外的任意字符防止匹配上下个""项目(也可以使用非贪婪匹配*?),以"结束
userlius = re.compile(r'[^\)]*\"')
#原理:主要通过空格和-来区分各不同项目,各项目内部写各自的匹配表达式
nginxlogpattern = re.compile(r"(%s)\ -\ -\ (%s)\ (%s)\ (%s)\ (%s)\ (%s)\ (%s)" %(ipp, timep, requestp, statusp, bodybytessentp, referp, useragentp), re.verbose)
#数据库连接信息
conn=mysqldb.connect(host='192.168.1.22',user='test',passwd='pass',port=3306,db='python')
cur=conn.cursor()
sql = "insert into python.test values(%s,%s,%s,%s,%s,%s,%s,%s,%s)"
while true:
line = logfile.readline()
if not line:break
matchs = nginxlogpattern.match(line)
if matchs != none:
allgroup = matchs.groups()
ip = allgroup[0]
time = allgroup[1]
request = allgroup[2]
status = allgroup[3]
bodybytessent = allgroup[4]
refer = allgroup[5]
useragent = allgroup[6]
time = time.replace('t',' ')[1:-7]
if len(useragent) > 20:
userinfo = useragent.split(' ')
userkel = userinfo[0]
try:
usersystem = usersystems.findall(useragent)
usersystem = usersystem[0]
print usersystem
userliu = userlius.findall(useragent)
value = [ip,time,request,status,bodybytessent,refer,userkel,usersystem,userliu[1]]
conn.commit()
print value
except indexerror:
userinfo = useragent
value = [ip,time,request,status,bodybytessent,refer,userinfo,"",""]
else:
useraa = useragent
value = [ip,time,request,status,bodybytessent,refer,useraa,"",""]
try:
result = cur.execute(sql,value)
#conn.commit()
print result
except mysqldb.error,e:
print "mysql error %d: %s" % (e.args[0], e.args[1])
conn.commit()
conn.close()
四、存入数据库后数据是如下图:
下一篇: Python pass 语句使用示例