如何在全局范围内向Python Logger对象添加处理程序?

时间:2016-02-23 12:12:49

标签: python logging

我想为我的项目创建一个记录器,它有一个自定义处理程序,可以在所有子模块中运行,并记录未捕获的异常。以下是我的概念验证;请注意,我使用文件处理程序作为最终将成为我的自定义处理程序的替代。

main.py:

import logging
import sys
from module import divide

logger = logging.getLogger(__name__)
logger.setLevel(logging.INFO)

fh = logging.FileHandler("test.log")
fh.setLevel(logging.INFO)
logger.addHandler(fh)

def uncaught_error(exc_type, exc_value, exc_traceback):
    logger.error("Uncaught Exception", exc_info = (exc_type, exc_value, exc_traceback))
    sys.__excepthook__(exc_type, exc_value, exc_traceback)
    return

sys.excepthook = uncaught_error

if __name__ == '__main__':
    logger.info("first division problem")
    print(divide(5,2))
    logger.info("second division problem")
    print(divide(10,0))
    logger.info("end")

module.py:

import logging

logger = logging.getLogger(__name__)

def divide(a, b):
    logger.info("dividing " + str(a) + " by " + str(b))
    return a/b

运行main.py之后,这是test.log的输出:

first division problem
second division problem
Uncaught Exception
Traceback (most recent call last):
  File "main.py", line 23, in <module>
    print(divide(10,0))
  File "/some/path/logging_test/module.py", line 7, in divide
    return a/b
ZeroDivisionError: division by zero

module.py中未捕获的异常记录得很漂亮,但行

logger.info("dividing " + str(a) + " by " + str(b))

显然没有做任何事情(也没有控制台输出)。这是什么错误?

3 个答案:

答案 0 :(得分:1)

我刚遇到这个问题,我的root日志格式没有在其他子模块中使用。我通过改变

解决了这个问题

logger = logging.getLogger(__name__)

在main.py模块中

logger = logging.getLogger()

以便实际获取root记录器而不是__main__记录器。

请参阅https://docs.python.org/2/library/logging.html#logging.getLogger

答案 1 :(得分:0)

我有类似的问题,这是我为解决这个问题所做的: -

module.py

import logging

def divide(a, b, logger):

    logger.info("dividing " + str(a) + " by " + str(b))
    return a/b

在main.py

通过将logger作为第三个参数

来调用divide()
print divide(5,2, logger)

在你的情况下,没有为module.py

设置处理程序

答案 2 :(得分:0)

将自定义处理程序添加到根记录器并完成。如果您没有更改任何其他内容(没有其他默认设置),只要您的其他记录器的级别允许,就会将所有模块的日志记录传递给该处理程序。

所有(其他)记录器都是根记录器的后代。 This diagram应该有助于了解日志记录中的信息流。