format参数中可能用到的格式化串:
%(name)s Logger的名字
%(levelno)s 数字形式的日志级别
%(levelname)s 文本形式的日志级别
%(pathname)s 调用日志输出函数的模块的完整路径名,交互模式可能没有
%(filename)s 调用日志输出函数的模块的文件名
%(module)s 调用日志输出函数的模块名
%(funcName)s 调用日志输出函数的函数名
%(lineno)d 调用日志输出函数的语句所在的代码行
%(created)f 当前时间,用UNIX标准的表示时间的浮 点数表示
%(relativeCreated)d 输出日志信息时的,自Logger创建以来的毫秒数
%(asctime)s 字符串形式的当前时间。默认格式是 “2003-07-08 16:49:45,896”。逗号后面的是毫秒
%(thread)d 线程ID。可能没有
%(threadName)s 线程名。可能没有
%(process)d 进程ID。可能没有
%(message)s 用户输出的消息
简单的pycharm输出
# -*- coding: UTF-8 -*-
import logging
logging.warning("user login")
logging.critical("server is down")
#E:\Python\学习\venv\Scripts\python.exe E:/整理版笔记/python/模块/loggin模块.py
WARNING:root:user login
CRITICAL:root:server is down
简单的py输出
import logging
logging.basicConfig(filename='log_test.log',
level=logging.INFO,
format='%(levelname)s '
'%(asctime)s '
'filename:%(filename)s '
'funcName:%(funcName)s '
'line:%(lineno)s '
'%(thread)d '
'%(threadName)s '
'%(process)d '
'%(message)s',
datefmt='%Y/%m/%d %H:%M:%S')
#datefmt='%Y/%m/%d %I:%M:%S %p')
def sayhai():
logging.error("sayhai.......")
sayhai()
logging.debug("debug")
logging.info("info")
logging.warning("warning")
运行结果 format 从简单到复杂的输出情况
Logging进阶写入到文件和屏幕输出
Python 使用logging模块记录日志涉及四个主要的类
1、logger提供了应用程序可以直接使用接口
2、handler将(logger创建的)日志记录发送到合适的目的输出
3、filter提供了细度设备来决定输出哪条日志记录
4、formatter决定日志记录的最终格式
相关代码
# -*- coding: UTF-8 -*-
import logging
from logging import handlers
class IgnoreBackupLogFileter01(logging.Filter):
'''忽略带 backup 的日志'''
def filter(self, record):#固定写法
return "backup" not in record.getMessage()
class IgnoreBackupLogFileter02(logging.Filter):
'''忽略带 db 的日志'''
def filter(self, record):#固定写法
return "db" not in record.getMessage()
#生成logger对象
logger = logging.getLogger("web")
logger.setLevel(logging.DEBUG) #全局日志级别
# 把filter对象添加到logger中
logger.addFilter(IgnoreBackupLogFileter01())
logger.addFilter(IgnoreBackupLogFileter02())
#生成handler对象
ch = logging.StreamHandler()
ch.setLevel(logging.INFO) #给ch handeler设置日志级别
#fh = logging.FileHandler("web.log")
#fh = handlers.RotatingFileHandler("web.log",maxBytes=50,backupCount=3)#按照大小保留日志的个数
fh = handlers.TimedRotatingFileHandler("web_data.log",when="s",interval=5,backupCount=5) #按照日期、天数、保留日志的个数
fh.setLevel(logging.WARNING) #给fh handeler设置日志级别
logger.addHandler(ch) #把handeler对象绑定到logger对象
logger.addHandler(fh) #把handeler对象绑定到logger对象
#生成formatter对象
file_fomatter = logging.Formatter(
'%(levelname)s '
'%(asctime)s '
'filename:%(filename)s '
'funcName:%(funcName)s '
'line:%(lineno)s '
'%(thread)d '
'%(threadName)s '
'%(process)d '
'%(message)s',
)
#生成formatter对象
console_fomatter = logging.Formatter(
'%(levelname)s '
'%(asctime)s '
'filename:%(filename)s '
'funcName:%(funcName)s '
'line:%(lineno)s '
'%(message)s',
)
#把formatter对象绑定到handler对象
ch.setFormatter(console_fomatter)
fh.setFormatter(file_fomatter)
logger.info("testlog")
logger.info("testlog")
logger.warning("testlog")
logger.info("db23123")
logger.info("backupasdfasdfa")
logger.warning("testlog")
#屏幕:INFO
#全局:DEBUG 默认级别是waring
#文件:waring
#总结、所有日志都会先走全局级别、当到了屏幕和文件的日志的时候、根据对应的日志级别筛选
#所以全局变量设置会影响屏幕和文件的日志信息,
#如果全局设置日志级别为error、屏幕和文件的日志级别设置DEBUG级,则文件日志和屏幕日志收不到error级别以下的日志信息、因为日志全局就已经被过滤掉了
#过滤关键字部分把 db backup部分已经过滤掉
#
D:\python\python.exe F:/运维笔记/python/模块/loggin模块进阶自动切割.py
INFO 2019-05-28 16:04:11,199 filename:loggin模块进阶自动切割.py funcName:<module> line:53 testlog
INFO 2019-05-28 16:04:11,199 filename:loggin模块进阶自动切割.py funcName:<module> line:54 testlog
WARNING 2019-05-28 16:04:11,199 filename:loggin模块进阶自动切割.py funcName:<module> line:55 testlog
WARNING 2019-05-28 16:04:11,201 filename:loggin模块进阶自动切割.py funcName:<module> line:58 testlog
logging.handlers.RotatingFileHandler("web.log",maxBytes=50,backupCount=3) #当文件到达一定大小后自动切割
logging.handlers.TimedRotatingFileHandler("web_data.log",when="s",interval=5,backupCount=5) #每间隔一段时间就自动切割日志
#日志切割
fh = handlers.TimedRotatingFileHandler("web_data.log",when="s",interval=5,backupCount=5) #interval
S - Seconds #秒
M - Minutes #分
H - Hours #小时
D - Days #天
midnight - roll over at midnight #每天0晨
W{0-6} - roll over on a certain day; 0 - Monday #W每星期 0代表星期一
扩展:Json格式文件
import logging
import logging.config
import json
ATTR_TO_JSON = ['created',
'filename',
'funcName',
'levelname',
'lineno',
'module',
'msg',]
class JsonFormatter:
def format(self, record):
obj = {attr: getattr(record, attr)
for attr in ATTR_TO_JSON}
return json.dumps(obj, indent=4)
handler = logging.StreamHandler()
handler.formatter = JsonFormatter()
logger = logging.getLogger(__name__)
logger.addHandler(handler)
logger.error("123")
#
D:\python\python.exe F:/运维笔记/python/模块/loggin模块进阶.py
{
"created": 1559033558.7925007,
"filename": "loggin\u6a21\u5757\u8fdb\u9636.py",
"funcName": "<module>",
"levelname": "ERROR",
"lineno": 21,
"module": "loggin\u6a21\u5757\u8fdb\u9636",
"msg": "123"
}