python - 如何通过warnings.warn抑制源上下文的打印?
问题描述
如果我将以下代码段放入文件中annoying.py
:
import warnings
message = 'I know! How about if we are just maximally annoying?!'
warnings.warn(message)
...并在 Unix shell 中运行它,这就是我得到的:
% python annoying.py
annoying.py:3: UserWarning: I know! How about if we are just maximally annoying?!
warnings.warn(message)
(我使用 Python 3.7.3 和 2.7.16 得到相同的输出。)
我只想打印此输出的第一行。
关于我正在做的事情,第二行只会增加视觉上分散注意力的混乱。(当有很多警告时,这种无缘无故的混乱变得特别成问题。)
如何抑制第二条/杂乱线?
解决方案
从warnings.py源代码看来, msg.line 控制是否需要打印额外的行。可以猴子修补 WarningMessage 的初始化,这样 self.line 是 "" 而不是 None 如下所示
import warnings
#modify the __init__ so that self.line = "" instead of None
def new_init(self, message, category, filename, lineno, file=None,
line=None, source=None):
self.message = message
self.category = category
self.filename = filename
self.lineno = lineno
self.file = file
self.line = ""
self.source = source
self._category_name = category.__name__ if category else None
warnings.WarningMessage.__init__ = new_init
message = 'I know! How about if we are just maximally annoying?!'
warnings.warn(message)
这导致:
annoying.py:19: UserWarning: I know! How about if we are just maximally annoying?!
另一种 hacky 方法可能是使用 -W 选项将警告作为错误出现:
% python -Werror::UserWarning annoying.py
如果您有以下烦恼.py
import warnings
message = 'I know! How about if we are just maximally annoying?!'
try:
warnings.warn(message)
except Exception as error:
print(error)
结果是
I know! How about if we are just maximally annoying?!
要获取文件名、行号、警告类型和警告消息,我必须执行以下操作
import warnings
import sys, os
message = 'I know! How about if we are just maximally annoying?!'
try:
warnings.warn(message)
except Exception as error:
exc_type, exc_obj, exc_tb = sys.exc_info()
fname = os.path.split(exc_tb.tb_frame.f_code.co_filename)[1]
print('{}:{}: {}: {}'.format(fname, exc_tb.tb_lineno,exc_type.__name__,exc_obj))
这导致
annoying.py:5: UserWarning: I know! How about if we are just maximally annoying?!