Une bibliothèque tierce (écrite en C) que j'utilise dans mon code python émet des avertissements. Je veux pouvoir utiliser le try
except
syntaxe pour gérer correctement ces avertissements. Existe-t-il un moyen de le faire?
Pour citer le manuel python ( 27.6.4. Tester les avertissements ):
import warnings
def fxn():
warnings.warn("deprecated", DeprecationWarning)
with warnings.catch_warnings(record=True) as w:
# Cause all warnings to always be triggered.
warnings.simplefilter("always")
# Trigger a warning.
fxn()
# Verify some things
assert len(w) == 1
assert issubclass(w[-1].category, DeprecationWarning)
assert "deprecated" in str(w[-1].message)
Pour gérer les avertissements comme des erreurs, utilisez simplement ceci:
import warnings
warnings.filterwarnings("error")
Après cela, vous pourrez détecter les avertissements comme les erreurs, par exemple cela fonctionnera:
try:
some_heavy_calculations()
except RuntimeWarning:
import ipdb; ipdb.set_trace()
P.S. Ajout de cette réponse car la meilleure réponse dans les commentaires contient une faute d'orthographe: filterwarnigns
au lieu de filterwarnings
.
Si vous voulez simplement que votre script échoue sur les avertissements, vous pouvez utiliser:
python -W error foobar.py
Voici une variante qui rend plus clair comment travailler avec uniquement vos avertissements personnalisés.
import warnings
with warnings.catch_warnings(record=True) as w:
# Cause all warnings to always be triggered.
warnings.simplefilter("always")
# Call some code that triggers a custom warning.
functionThatRaisesWarning()
# ignore any non-custom warnings that may be in the list
w = filter(lambda i: issubclass(i.category, UserWarning), w)
if len(w):
# do something with the first warning
email_admins(w[0].message)
Dans certains cas, vous devez utiliser des ctypes pour transformer les avertissements en erreurs. Par exemple:
str(b'test') # no error
import warnings
warnings.simplefilter('error', BytesWarning)
str(b'test') # still no error
import ctypes
ctypes.c_int.in_dll(ctypes.pythonapi, 'Py_BytesWarningFlag').value = 2
str(b'test') # this raises an error