如何防止记录器多次打印相同的信息?

时间:2017-10-30 05:56:08

标签: python logging

当我多次实例化MyClass时,相同的记录会多次出现在日志中(在类的第二次或第三次初始化之后)。

这些建议已经改善了这个解决方案:

Duplicate log output when using Python logging module

Python logging module is printing lines multiple times

我的记录器解决方案如下所示:

import logging
import logging.handlers
import os

OUTPUT_DIRECTORY_PATH   = r'..\out'
LOG_DIRECTORY_PATH      = os.path.join(OUTPUT_DIRECTORY_PATH, "logs")

loggers = {}
def PlatformLogger(moduleName):

    global loggers

    if loggers.get(moduleName):

        return loggers.get(moduleName)

    else:

        # create logger with moduleName parameter
        logger = logging.getLogger(moduleName)
        logger.setLevel(logging.DEBUG)

        # create console handler with a higher log level
        ch = logging.StreamHandler()
        ch.setLevel(logging.INFO)

        # create file handler which logs even debug messages
        fh = logging.FileHandler(os.path.join(LOG_DIRECTORY_PATH, 'error.log'))
        fr = logging.handlers.RotatingFileHandler(os.path.join(LOG_DIRECTORY_PATH, 'event.log'))
        fh.setLevel(logging.WARN)
        fr.setLevel(logging.DEBUG)

        # create formatter and add it to the handlers
        formatter = logging.Formatter('[%(asctime)s] - %(name)s - %(levelname)s - %(message)s')
        fh.setFormatter(formatter)
        fr.setFormatter(formatter)
        ch.setFormatter(formatter)

        # add the handlers to the logger
        logger.addHandler(fh)
        logger.addHandler(fr)
        logger.addHandler(ch)

        # updating loggers
        loggers.update(dict(name=logger))

        return logger


class MyClass:

    def __init__(self):
        self.logger = PlatformLogger(__name__)

    def doSomething(self, actionName):
        self.logger.info("action: " + actionName)



dm1 = MyClass()
dm1.doSomething("action 1")
dm2 = MyClass()
dm2.doSomething("action 2")  # <- this is prited twice

日志中包含的内容:

[2017-10-30 06:47:45,198] - __main__ - INFO - action: action 1
[2017-10-30 06:47:45,201] - __main__ - INFO - action: action 2
[2017-10-30 06:47:45,201] - __main__ - INFO - action: action 2

我做错了什么?我该怎么做才能防止这种行为?

1 个答案:

答案 0 :(得分:1)

而不是loggers.update(dict(name=logger)),您必须写loggers.update({moduleName: logger})

在行logger = logging.getLogger(moduleName)中,您始终可以通过其名称获得相同的记录器。因此,每次实例化类时,都会向记录器添加新的处理程序,每个处理程序都会打印一行。您必须在模块级别上仅配置一次所有日志记录。