Comment obtenir le message d'exception en Python correctement
Quelle est la meilleure façon d'obtenir des exceptions " messages à partir des éléments de la bibliothèque standard de Python?
J'ai remarqué que dans certains cas, vous pouvez l'obtenir via message
champ comme ceci:
try:
pass
except Exception as ex:
print(ex.message)
mais dans certains cas (par exemple, en cas de prise d'erreurs) que vous avez à faire quelque chose comme ceci:
try:
pass
except socket.error as ex:
print(ex)
Je me demandais est-il de toute façon standard pour couvrir la plupart de ces situations?
- Vous êtes l'amalgame entre deux choses différentes -
except Foo as bar:
est le même queexcept Foo, bar:
(à l'exception de l'ancien est plus récente, et continuera de travailler en 3.x), si l'erreur vient avec unmessage
attribut ou de ne pas se séparer. - Demandez-vous si l'accès
.message
pour une erreur est standard ou pas? - votre deuxième exemple avec
print(msg)
est juste un raccourci pourprint(str(msg))
- S Kumar Yep. Il travaillera dans tous les cas?
- Je crois que l'accès
message
est obsolète. - stackoverflow.com/questions/1272138/...
Vous devez vous connecter pour publier un commentaire.
Si vous regardez la documentation pour les erreurs intégrées, vous verrez que la plupart des
Exception
classes affecter leur premier argument comme unmessage
attribut. Pas tous les faire bien.Notamment,
EnvironmentError
(avec des sous-classesIOError
etOSError
) le premier argument deerrno
, deuxième destrerror
. Il n'y a pas demessage
...strerror
est à peu près similaire à ce qui serait normalement unmessage
.Plus généralement, les sous-classes de
Exception
peuvent faire ce qu'ils veulent. Ils peuvent ou peuvent ne pas avoir unmessage
attribut. Futur intégréException
s ne peut pas avoir unmessage
attribut. ToutException
sous-classe importés à partir de bibliothèques de tiers ou de l'utilisateur, le code ne peut pas avoir unmessage
attribut.Je pense que la bonne façon de ce traitement est d'identifier le
Exception
sous-classes que vous voulez prendre, et puis prendre seulement ceux-ci au lieu de tout avec unexcept Exception
, puis utiliser quelles que soient les attributs spécifiques de la sous-classe définit comme vous le souhaitez.Si vous devez
print
quelque chose, je pense que l'impression de la prisException
lui-même est le plus susceptible de faire ce que vous voulez, si elle a unmessage
attribut ou pas.Vous pouvez aussi vérifier que le message de l'attribut si vous le vouliez, comme ça, mais je ne serais pas vraiment suggérer comme il semble le désordre:
str(ex)
au lieu de simplementex
?str()
pour vous. Il n'y a pas de raison manuellement l'appel vous-même, bien qu'il est inoffensif depuis l'appel destr()
sur une chaîne de juste retour de la chaîne elle-même.str()
si le message est de typeunicode
.Pour améliorer la réponse fournie par @artofwarfare, voici ce que je considère un plus propre façon de vérifier pour la
message
de l'attribut et de l'imprimer ou imprimer leException
objet comme une solution de repli.L'appel à
repr
est facultatif, mais je trouve ça nécessaire dans certains cas d'utilisation.Mise à jour #1:
Suivant le commentaire de @MadPhysicist, voici une preuve que l'appel à
repr
peut être nécessaire. Essayez d'exécuter le code suivant dans votre interprète:Mise à jour #2:
Voici une démo avec des spécificités pour Python 2.7 et 3.5: https://gist.github.com/takwas/3b7a6edddef783f2abddffda1439f533
getattr
lève une exception si l'objet passé en n'ont pas demandé d'attribut. Si vous vouliez faire quelque chose comme ça, je pense que vous devriez utiliser le troisième argument optionnel pourgetattr
, comme ceci:print getattr(e, 'message', e)
. Discutable de mieux que ce que j'ai fait. Une autre option seraitprint(e.message if hasattr(e, 'message') else e)
.str
au lieu derepr
.repr
.str
,repr
ajoute simplement le nom de la classe. Au lieu d'utiliserrepr
, j'aimerais proposer l'utilisation d'print('{e.__class__.__name__}: {e}'.format(e=e))
. La sortie d'impression est plus propre et adhère à la sortie de l'élever lui-même.'{e.__class__.__module__}.{e.__class__.__name__}: {e}'
J'ai eu le même problème. Je pense que la meilleure solution est d'utiliser le journal.exception, qui sera automatiquement imprimer la trace de la pile et de message d'erreur, tels que:
log
? J'ai juste essayé deimport log
sur Python 2.7.13 et reçu un message qu'il n'y a pas de module de ce nom. Est-ce quelque chose que vous avez ajoutés viapip
ou y avait-il ajouté dans une version plus récente de python (je sais, je sais, j'ai besoin de mettre à jour vers Python 3... je vais le faire dès que CentOS cesse d'expédition avec Python 2 par défaut...)import logging
\nlog = logging.getLogger(__name__)