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

时间:2021-07-20 13:31:31

标签: python logging

我正在尝试创建一个应该在 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 级别的日志?

3 个答案:

答案 0 :(得分:0)

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

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")

答案 1 :(得分:0)

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

记录器本身有一个由

设置的日志记录级别
logger.setLevel(logging.INFO)

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

handler.setLevel(logging.INFO)

例如,您可以在 WARNING 级别使用 FileHandler 日志记录,在 INFO 级别使用 StreamHandler 日志记录。

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

答案 2 :(得分:0)

对现有答案进行一些补充:

  1. 对于像这样的简单日志配置,使用 logging.basicConfig 如 Python 中的 this example 中所述 文档。它自动记录根记录器的级别和 它的处理程序。

    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