logging
filter & dictConfig
项目中需要改造之前的垃圾日志输出和配置形式,研究了一下logging模块的字典配置和filter过滤器功能。
demo如下(部分摘自python官网文档):
talk is cheap, show you code!
'''
介绍logging config模块功能,for example
'''
import logging.config
import logging
# 自定义filter功能
class MyFilter(logging.Filter):
'''
继承logging.Filter,并复写filter方法
'''
def __init__(self, param=None, param2=None):
'''
param:参数是定义的filter中的param字段
'''
self.param = param
self.param2 = param2
def filter(self, record):
def param(x): return x not in record.msg
if self.param is None:
allow = True
else:
allow = all(param(x) for x in self.param)
# allow = self.param not in record.msg
if allow:
record.msg = 'changed: ' + record.msg # filter可以对匹配的规则做一些特殊处理
# 如果有key关键字,则在msg中加上value信息,单纯测试,目前没看到实际应用的场景
if self.param2 is not None:
for x in self.param2.keys():
if not param(x):
record.msg = '{}'.format(self.param2[x]) + record.msg
return allow
# config是一个字典,dictConfig解析字典数据
LOGGING = {
'version': 1.0,
'formatters': {
'f1': {
'format': '%(levelname)-8s %(asctime)s %(name)-8s %(filename)-15s:%(lineno)-3d %(threadName)-10s %(thread)-15d %(message)s'
}
},
'filters': {
'myfilter': {
'()': MyFilter, # 定义的类
'param': ['noshow', 'nodisplay'], # 传给param的参数列表
'param2': {'key': 'value'} # 测试是否支持另一种形式
}
},
'handlers': {
'console': {
'class': 'logging.StreamHandler',
'formatter': 'f1',
'filters': ['myfilter'],
'level': 'DEBUG'
},
'info': {
'class': 'logging.handlers.TimedRotatingFileHandler',
'formatter': 'f1',
'filename': 'logconfig_info.log',
'level': 'INFO',
'when': 'M',
'backupCount': 180
},
'error': {
'class': 'logging.handlers.TimedRotatingFileHandler',
'formatter': 'f1',
'filename': 'logconfig_error.log',
'level': 'ERROR',
'when': 'M',
'backupCount': 180
}
},
'logger': { # 未使用到之中模式,除非代码中各个模块使用了不同的日志输出格式等才可能有用吧
'abc': {
'handlers': ['console']
},
'a.b.c': {
'handlers': ['info']
}
},
# root是所有定义的logger的父日志记录器
'root': {
'handlers': ['console', 'info', 'error'],
'level': 'DEBUG' # root默认是warning的,所以需要将root level设置为DEBUG,通过handler中的level进行控制
}
}
logging.config.dictConfig(LOGGING)
logger3 = logging.getLogger(__name__)
logger1 = logging.getLogger('abc')
while True:
try:
import time
logger3.error('hello world')
logger3.warning('helloworld')
logger3.info('hw')
logger3.info('hw noshow')
logger3.info('hw nodisplay')
logger3.debug('GET /')
logger3.debug('POST / key')
logger1.debug('logger1...')
time.sleep(2)
except KeyboardInterrupt:
break
'''
日志输出:
ERROR 2020-04-30 15:06:09,538 __main__ logging_config.py:104 MainThread 6692 changed: hello world
WARNING 2020-04-30 15:06:09,540 __main__ logging_config.py:105 MainThread 6692 changed: helloworld
INFO 2020-04-30 15:06:09,540 __main__ logging_config.py:106 MainThread 6692 changed: hw
DEBUG 2020-04-30 15:06:09,540 __main__ logging_config.py:109 MainThread 6692 changed: GET /
DEBUG 2020-04-30 15:06:09,540 __main__ logging_config.py:110 MainThread 6692 valuechanged: POST / key
DEBUG 2020-04-30 15:06:09,540 abc logging_config.py:112 MainThread 6692 changed: logger1...
'''
总结
- 好好看官方文档,大有裨益!