在日志模块中添加了新的日志级别verbose
。它可以正常工作,但是与它沿着记录的文件名不正确。它总是显示日志模块名称,而不是触发日志的模块。
下面是记录器模块代码,
class _CustomRotatingFileHandler(logging.handlers.RotatingFileHandler):
def __init__(self, *args, **kwargs):
prev_umask = os.umask(0o000)
super().__init__(*args, **kwargs)
os.umask(prev_umask)
def doRollover(self):
prev_umask = os.umask(0o000)
super().doRollover()
os.umask(prev_umask)
def setup_logging():
reference = 'my_project'
date_fmt = '%(asctime)s %(levelname)s %(filename)s:%(lineno)d' \
' : %(message)s'
# Defining a custom log level for verbose log level
# selected a value between logging.INFO and logging.DEBUG
log_level_verbose = 15
logging.addLevelName(log_level_verbose, 'VERBOSE')
logger = logging.getLogger(reference)
logger.setLevel(logging.DEBUG)
# For custom log level verbose
log_func = lambda msg, *args, **kwargs: logger.log(log_level_verbose, msg, *args, **kwargs) # noqa: E731
setattr(logger, 'verbose', log_func)
file_handler = _CustomRotatingFileHandler(
log_file, maxBytes=10485760, backupCount=3
)
file_log_format = logging.Formatter(date_fmt, "%b %e %H:%M:%S")
file_handler.setFormatter(file_log_format)
file_handler.setLevel(log_level_verbose)
console_handler = logging.StreamHandler(sys.stdout)
console_log_format = logging.Formatter("%(message)s")
console_handler.setFormatter(console_log_format)
console_handler.setLevel(logging.INFO)
logger.handlers = [file_handler, console_handler]
return logger
这里创建的verbose
级别是只将消息记录到日志文件,不记录到控制台,流程是main.py
通过调用setup_logging
创建logger对象,并将此logger对象传递给test_module.py
函数执行并记录。
日志文件内容如下所示,其中VERBOSE消息仅记录在文件中(如预期),但与其沿着记录的文件名错误,应为test_module.py
Feb 4 16:54:31 INFO main.py:151 : ----------------------
Feb 4 16:54:31 INFO main.py:152 : Executing command for 'task1'
Feb 4 16:54:31 INFO main.py:153 : ----------------------
Feb 4 16:54:31 INFO test_module.py:34 : Executing command 'ls -ltr'
Feb 4 16:54:31 VERBOSE log.py:88 : Some verbose log message
Feb 4 16:54:32 INFO test_module.py:37 : Result: total 24
-rwxr-xr-x. 1 root root 20606 Jan 13 13:31 main.py
Feb 4 16:54:32 INFO main.py:160 : Completed
目前,对于VERBOSE日志,我收到如下日志消息,
2月4日16:54:31详细日志患者:88:一些冗长的日志消息
具有正确文件名的预期日志消息应如下所示,
2月4日16:54:31详细测试_模块.py:35:一些冗长的日志消息
1条答案
按热度按时间pcww981p1#
最后我得到了答案。这是被修改的代码行,
从
logger.log
更改为logger._log
,参数*args
更改为args
。我在How to add a custom loglevel to Python's logging facility中@rivy的一条回答评论中找到了这背后的确切原因。
需要使用_log()而不是log()来避免在调用堆栈中引入额外的级别。如果使用log(),则额外堆栈帧的引入会导致多个LogRecord属性(funcName、lineno、filename、pathname...)指向调试函数而不是实际调用方。
这正是filename不能正确使用
logger.log
的原因