在运行logging.basicConfig之前如何使用Python日志?
看起来如果你在运行 logging.basicConfig
之前就调用了 logging.info()
,那么 logging.basicConfig
的设置就不会起作用。实际上,这时候不会有任何日志记录。
这个行为在哪里有说明呢?我不是很明白。
7 个回答
11
卡洛斯·A·伊巴拉的这个回答原则上是对的,不过他的实现可能会出问题,因为你在遍历一个可能会被调用removeHandler()改变的列表。这是不安全的。
有两个替代方案:
while len(logging.root.handlers) > 0:
logging.root.removeHandler(logging.root.handlers[-1])
logging.basicConfig(format='%(asctime)s %(message)s',level=logging.DEBUG)
或者:
logging.root.handlers = []
logging.basicConfig(format='%(asctime)s %(message)s',level=logging.DEBUG)
这两个方案中,第一个使用循环的方式是最安全的(因为任何处理程序的销毁代码可以在日志框架内部显式调用)。不过,这还是一种变通方法,因为我们依赖于logging.root.handlers是一个列表。
13
是的。
你想要记录一些信息,所以记录功能需要先设置一个默认的配置。一旦设置好了记录功能……嗯……就算是配置完成了。
“配置好记录器对象后,下面的方法可以用来创建日志信息。”
另外,你可以了解一下如何创建处理器,以避免不必要的日志记录。但这更多是针对糟糕实现的一个小技巧,而不是一个实用的技术。
这里有个小窍门。
没有任何模块可以在全局范围内做其他事情,除了调用
logging.getLogger()
。只有
if __name__ == "__main__":
这一部分可以进行日志配置。
如果你在模块的全局范围内进行日志记录,那么可能会强制日志系统生成它的默认配置。
不要在任何模块的全局范围内使用 logging.info
。如果你真的觉得必须在模块的全局范围内使用 logging.info
,那么你必须在导入其他内容之前先配置日志。这会导致脚本看起来不太好。
56
你可以像这样去掉默认的处理程序,并重新设置日志记录:
# if someone tried to log something before basicConfig is called, Python creates a default handler that
# goes to the console and will ignore further basicConfig calls. Remove the handler if there is one.
root = logging.getLogger()
if root.handlers:
for handler in root.handlers:
root.removeHandler(handler)
logging.basicConfig(format='%(asctime)s %(message)s',level=logging.DEBUG)