首页 文章

登录模块:无法找到 Logger 的处理程序

提问于
浏览
1

我正在尝试使用在可执行文件中配置的 Logger 启用模块中的日志记录 .

根据documentation

命名 Logger 时使用的一个好习惯是在每个使用日志记录的模块中使用模块级 Logger ,命名如下:

logger = logging.getLogger(__name__)

我已经遵循了这一点,在我的 foo 模块中创建了一个模块级 Logger :

module foo:

import logging

logger = logging.getLogger(__name__)

class Foo():
    def __init__(self):
        logger.info("hello world")

再次,根据documentation

使用调用上面列出的配置方法的Python代码显式创建 Logger ,处理程序和格式化程序 .

在我的可执行文件中,我导入 foo 并设置 Logger ,基本上是上面文档链接示例的复制粘贴:

executable:

import logging
from foo import foo

if __name__ == '__main__':

    # create logger
    logger = logging.getLogger(__name__)
    logger.setLevel(logging.DEBUG)

    # create console handler and set level to debug
    ch = logging.StreamHandler()
    ch.setLevel(logging.DEBUG)

    # add ch to logger
    logger.addHandler(ch)

    logger.info('start')

    f = foo.Foo()

我从我的可执行文件中看到了日志语句,但我的基于模块的 Logger 不起作用:

开始
没有为logger“foo.foo”找到处理程序

我究竟做错了什么?

Edit:

我尝试在我的可执行文件中使用 basicConfig ,根据documentation执行以下操作:

通过使用默认Formatter创建StreamHandler并将其添加到根 Logger 来为日志记录系统进行基本配置

executable:

import logging
from foo import foo

if __name__ == '__main__':

    # create logger
    logger = logging.getLogger(__name__)
    ... (same as above) ...

    logging.basicConfig(level=logging.DEBUG)

    logger.info('start')

    f = foo.Foo()

现在登录我的模块工作!

令我困惑的是,在我之前的示例中,我正在创建 StreamHandler 并将其添加到根 Logger .

所以我想我的问题应该是:

What is basicConfig doing which explicit calls to the logging configuration api isn't?

1 回答

  • 1

    您还需要将处理程序分配给 Foo 模块 Logger ,因为它们使用不同的 Logger 对象:

    import logging
    
    logger = logging.getLogger(__name__)
    sh = logging.StreamHandler()
    logger.setLevel(logging.DEBUG)
    logger.addHandler(sh)
    
    class Foo():
        def __init__(self):
            logger.info("hello world")
    
    ==================== RESTART: C:\Python27\tests\test2.py ====================
    start
    hello world
    

    或者您可以使用日志记录模块中的 basicConfig 函数来更改根 Logger 和新 Logger 的默认值:

    if __name__ == '__main__':
        sh = logging.StreamHandler()
        logging.basicConfig(level=logging.DEBUG)
        root = logging.getLogger(__name__)
        root.info('start')
        f = Foo()
    

    一个很好的日志资源 - Python Logging Cookbook


    根据新问题更新:

    通过使用默认Formatter创建StreamHandler并将其添加到根 Logger 来为日志记录系统进行基本配置 . 如果没有为根 Logger 定义处理程序,函数debug(),info(),warning(),error()和critical()将自动调用basicConfig() .

    在您的代码中,每个模块都有自己的 Logger 对象 . 您需要为每个指定处理程序和配置 . 基本配置基本上为您设置了一些默认值 - 如果您没有明确说明它们 . 所有 Logger 对象都是从根 Logger 派生的,因此您可以更改根 Logger 的默认值,然后新的 Logger 派生它 .

相关问题