首页 文章

Python登录几个模块输出两次

提问于
浏览
1

我对python日志记录不是很熟悉,我试图将它输出到控制台 . 我已经让它工作,但似乎输出在控制台中看到两次,我不知道为什么 . 我看过这里提到的其他类似情况但我找不到任何帮助我的问题 .

我有三个模块,我们称之为 mambmcmain . 主要导入这3个模块并调用它们的功能 .

在每个模块中,我设置了一个这样的 Logger :

ma.py

import logging
logger = logging.getLogger('test.ma') #test.mb for mb.py/test.mc for mc.py
logger.setLevel(logging.DEBUG)

console_log = logging.StreamHandler()
console_log.setLevel(logging.DEBUG)
formatter = logging.Formatter('%(asctime)s - %(name)s - %(message)s')
console_log.setFormatter(formatter)
logger.addHandler(console_log)
...
...
#right before the end of each module, after I'm finished logging what I need.
logger.removeHandler(console_log)

mb.py

import logging
logger = logging.getLogger('test.mb')
logger.setLevel(logging.DEBUG)

console_log = logging.StreamHandler()
console_log.setLevel(logging.DEBUG)
formatter = logging.Formatter('%(asctime)s - %(name)s - %(message)s')
console_log.setFormatter(formatter)
logger.addHandler(console_log)
...
...
#end of file
logger.removeHandler(console_log)

mc.py

import logging
logger = logging.getLogger('test.mc')
logger.setLevel(logging.DEBUG)

console_log = logging.StreamHandler()
console_log.setLevel(logging.DEBUG)
formatter = logging.Formatter('%(asctime)s - %(name)s - %(message)s')
console_log.setFormatter(formatter)
logger.addHandler(console_log)
...
...
#end of file
logger.removeHandler(console_log)

我遇到的主要问题是输出打印两次,对于程序的某些部分,它没有格式化 . 任何帮助将不胜感激,谢谢!

2 回答

  • 1

    使用全局 Logger 的更好方法是使用包含对 logging.getLogger 的调用的函数:

    import logging
    
    def get_logger(name):
        logger = logging.getLogger(name)
        if not logger.handlers:
            # Prevent logging from propagating to the root logger
            logger.propagate = 0
            console = logging.StreamHandler()
            logger.addHandler(console)
            formatter = logging.Formatter('%(asctime)s - %(name)s - %(message)s')
            console.setFormatter(formatter)
        return logger
    
    def main():
        logger = get_logger(__name__)
        logger.setLevel(logging.DEBUG)
        logger.info("This is an info message")
        logger.error("This is an error message")
        logger.debug("This is a debug message")
    
    if __name__ == '__main__':
        main()
    

    Output

    2017-03-09 12:02:41,083 - __main__ - This is an info message
    2017-03-09 12:02:41,083 - __main__ - This is an error message
    2017-03-09 12:02:41,083 - __main__ - This is a debug message
    

    Note: 使用函数还允许我们将 logger.propagate 设置为 False 以防止将日志消息发送到根 Logger . 这几乎可以肯定是您所看到的重复输出的原因 .

    Update: 调用 get_logger 后,必须通过调用 logger.setLevel 来设置所需的级别 . 如果不这样做,则只会看到错误消息 .

  • 0

    要将多个模块登录到一个全局文件,请创建一个日志记录实例,然后在您喜欢的任何模块中获取该实例 . 所以例如在main中,我会:

    import logging
    
    logging.basicConfig(filename='logfile.log', level=logging.DEBUG)
    formatter = logging.Formatter('%(asctime)s - %(name)s - %(message)s')
    logger = logging.getLogger('Global Log')
    

    然后,在我希望能够附加到此日志的每个模块中,我有:

    import logging
    logger = logging.getLogger('Global Log')
    

    现在,每次访问模块中的 Logger 时,您都在访问相同的记录实例 . 这样,您只需设置一次 Logger 并将其格式化 .

    有关在文档中记录实例的更多信息:https://docs.python.org/2/library/logging.html#logging.getLogger

相关问题