繁体   English   中英

自定义记录器不会覆盖根日志级别

[英]Custom logger not overwriting root log level

我正在尝试创建一个应该在 INFO 级别记录的自定义记录器。 代码如下所示:

import logging

logger = logging.getLogger(__name__)

# write to stderr
handler = logging.StreamHandler()
handler.setLevel(logging.INFO)

# format log message
formatter = logging.Formatter("%(asctime)s: %(levelname)s:%(name)s - %(message)s")
handler.setFormatter(formatter)

logger.addHandler(handler)

logger.debug("This is a debug message")
logger.info("This is an info message")
logger.warning("This is a warning message")
logger.error("This is an error message")
logger.critical("This is a critical message")

结果输出是:

2021-07-20 15:24:51,148: WARNING:__main__ - This is a warning message
2021-07-20 15:24:51,149: ERROR:__main__ - This is an error message
2021-07-20 15:24:51,149: CRITICAL:__main__ - This is a critical message

我希望输出也包含信息级别的日志,但正如您所看到的那样。 但是,如果我更改为handler.setLevel(logging.ERROR)输出如下所示:

2021-07-20 15:27:49,864: ERROR:__main__ - This is an error message
2021-07-20 15:27:49,864: CRITICAL:__main__ - This is a critical message

因此,如果我的限制比根记录器更严格,它会覆盖,但如果我的限制较少,则不会。 如何让自定义记录器记录 INFO 级别的日志?

您需要像这样在记录器实例上设置日志级别:

import logging

logger = logging.getLogger(__name__)
# write to stderr
handler = logging.StreamHandler()
handler.setLevel(logging.INFO)
logger.setLevel(logging.INFO)

# format log message
formatter = logging.Formatter("%(asctime)s: %(levelname)s:%(name)s - %(message)s")
handler.setFormatter(formatter)


logger.addHandler(handler)

logger.debug("This is a debug message")
logger.info("This is an info message")
logger.warning("This is a warning message")
logger.error("This is an error message")
logger.critical("This is a critical message")

好的,lee-pai-long 的回答解决了这个问题,但我又读了一些,现在我明白了为什么它会这样工作。

记录器本身有一个由设置的日志记录级别

logger.setLevel(logging.INFO)

记录器可以连接一个或多个处理程序,每个处理程序都可以有自己的日志记录级别。

handler.setLevel(logging.INFO)

例如,您可以在 WARNING 级别有一个 FileHandler 日志记录,在 INFO 级别有一个 StreamHandler 日志记录。

因此,导致该错误的原因是处理程序设置为 INFO,但从未设置记录器的级别,使其默认为 WARNING 的根级别。

对现有答案的一些补充:

  1. 对于像这样的简单日志配置,请使用 Python 文档中此示例中所述的logging.basicConfig 它会自动记录根记录器及其处理程序的级别。

     logging.basicConfig(format='%(levelname)s:%(message)s', level=logging.DEBUG)
  2. 要调查整个日志记录器树(及其处理程序、格式化程序和过滤器)的状态,请使用logging_tree 如果我在问题的片段末尾添加了这个。

     import logging_tree logging_tree.printout()

    这很清楚地表明正在发生。 它在更复杂的logging配置中特别有用。

     <--"" Level WARNING | o<--"__main__" Level NOTSET so inherits level WARNING Handler Stream <_io.TextIOWrapper name='<stderr>' mode='w' encoding='utf-8'> Level INFO Formatter fmt='%(asctime)s: %(levelname)s:%(name)s - %(message)s' datefmt=None

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM