帮助我理解python';s日志模块及其处理程序
我真的很怀念python日志模块的一些基本内容 在下面的代码中,我创建了一个logger对象(帮助我理解python';s日志模块及其处理程序,python,logging,Python,Logging,我真的很怀念python日志模块的一些基本内容 在下面的代码中,我创建了一个logger对象(log),并向其中添加了两个处理程序。一个 “信息”级别和“警告”级别。它们都应该打印到标准输出。我希望调用log.info(msg) 将在我的stdout中生成一份msg,并调用log.warn(msg)sould result 两份msg打印到我的stdout。代码如下: import logging import sys logging.basicConfig() log = logging.
log
),并向其中添加了两个处理程序。一个
“信息”级别和“警告”级别。它们都应该打印到标准输出。我希望调用log.info(msg)
将在我的stdout中生成一份msg
,并调用log.warn(msg)
sould result
两份msg
打印到我的stdout。代码如下:
import logging
import sys
logging.basicConfig()
log = logging.getLogger('myLogger')
log.handlers = []
h1 = logging.StreamHandler(sys.stdout)
h1.level = logging.INFO
h1.formatter = logging.Formatter('H1 H1 %(message)s ')
h2 = logging.StreamHandler(sys.stdout)
h2.level = logging.WARNING
h2.formatter = logging.Formatter('H2 H2 %(message)s')
log.addHandler(h1)
log.addHandler(h2)
print 'log.level == %s'%logging.getLevelName(log.level)
print 'log.info'
log.info('this is some info')
print 'done'
print 'log.warn'
log.warn('this is a warning')
print 'done'
输出对我来说真的很奇怪。.info
调用不会产生视觉效果。
但是,调用warn
会将两份msg打印到stdout(这是正常的),但也会将一份msg打印到stderr(为什么?)。这是上述代码的输出。请注意此输出中最后一行的格式。这行打印到stderr
log.level == NOTSET
log.info
done
log.warn
H1 H1 this is a warning
H2 H2 this is a warning
done
WARNING:myLogger:this is a warning
因此,我的问题是:
info
的调用导致没有输出,尽管h1
的级别设置为infowarn
会导致额外的输出到stderr实际上,日志记录有五个级别:调试、信息、警告、错误和关键。我发现,当您设置记录器时,您没有显式地设置级别——我相信,如果未设置级别,记录器可能会默认为警告 至于为什么它会多次打印出来作为警告,我相信这是由于您为信息和警告创建了两个处理程序。所发生的情况是,记录器从警告->信息->调试逐级降低严重性,并为每个事件调用处理程序。由于您的级别设置为警告,信息处理程序将被忽略。此外,我认为警告消息通常会写入sys.stderr 请尝试以下操作:
logging.basicConfig(level=logging.INFO)
另见:
- 根记录器初始化为
如果到达记录器的任何日志消息的级别低于记录器的级别,则会丢弃该日志消息。如果未设置记录器的级别,它将从其父记录器获取其“有效级别”。因此,如果根记录器的级别为警告级别
,则所有记录器的默认有效级别为警告
。如果不进行其他配置,则将丢弃级别低于该级别的所有日志消息警告
- 当您调用
时,系统会在根记录器上自动设置一个basicConfig()
,该记录器将打印到标准错误流。 当您的程序打印出其日志消息时,实际上有三个处理程序:您添加的两个处理程序,它们有自己的级别,以及来自系统的一个处理程序,它将打印出未被记录器拒绝的任何消息。这就是为什么你要排队StreamHandler
它来自系统记录器。它不会对WARNING:myLogger:this is a warning
级别消息执行此操作,因为如前所述,根记录器配置为默认拒绝这些消息 如果不需要此输出,请不要调用INFO
basicConfig()
- 有两件事你需要知道:
进一步阅读:我不确定,但你可能会遇到麻烦,因为python的
日志记录
有一个内置的警告和信息级别。@brc这将回答我的第一个问题,但不是第二个问题。哈,和我一样,抓住了我的错误——不知何故,这让我发了两个帖子?更具体地说,在他的示例中,@bgbg设置处理程序的级别,但从不设置记录器的级别。因此,记录器的级别默认为logging.WARNING
。添加log.level=logging.INFO
将解决此问题。我同意@davidz的观点,即最好完全删除basicConfig()
调用,而不依赖于根记录器。