Цепочка исключений Python [дубликат]



этот вопрос уже есть ответ здесь:




  • "Внутреннее исключение" (с трассировкой) в Python?

    8 ответов



существует ли стандартный способ использования цепочек исключений в Python? Как исключение Java "вызвано"?



вот некоторые фон.



у меня есть модуль с одним основным классом исключений DSError:



 class DSError(Exception):
pass


где-то внутри этого модуля будет:



try:
v = my_dict[k]
something(v)
except KeyError as e:
raise DSError("no key %s found for %s" % (k, self))
except ValueError as e:
raise DSError("Bad Value %s found for %s" % (v, self))
except DSError as e:
raise DSError("%s raised in %s" % (e, self))


в основном этот фрагмент должен бросить только DSError и рассказать мне, что произошло и почему. Дело в том, что блок try может бросить много других исключений, поэтому я предпочел бы, если я могу сделать что-то вроде:



try:
v = my_dict[k]
something(v)
except Exception as e:
raise DSError(self, v, e) # Exception chained...


это стандарт для Python способ? Я не видел цепочек исключений в других модулях, так как это делается в Python?

735   2  

2 ответов:

исключения-цепочки доступно только в Python 3, где вы можете написать:

try:
    v = {}['a']
except KeyError as e:
    raise ValueError('failed') from e

, который дает выход как

Traceback (most recent call last):
  File "t.py", line 2, in <module>
    v = {}['a']
KeyError: 'a'

The above exception was the direct cause of the following exception:

Traceback (most recent call last):
  File "t.py", line 4, in <module>
    raise ValueError('failed') from e
ValueError: failed

в большинстве случаев, вам даже не нужно from; Python 3 по умолчанию показывает все исключения, которые произошли во время обработки исключений, например:

Traceback (most recent call last):
  File "t.py", line 2, in <module>
    v = {}['a']
KeyError: 'a'

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "t.py", line 4, in <module>
    raise ValueError('failed')
ValueError: failed

что вы можете сделать в Python 2 добавляет пользовательские атрибуты в класс исключений, например:

class MyError(Exception):
    def __init__(self, message, cause):
        super(MyError, self).__init__(message + u', caused by ' + repr(cause))
        self.cause = cause

try:
    v = {}['a']
except KeyError as e:
    raise MyError('failed', e)

это то, что вы просите?

class MyError(Exception):
    def __init__(self, other):
        super(MyError, self).__init__(other.message)

>>> try:
...     1/0
... except Exception, e:
...     raise MyError(e)
Traceback (most recent call last):
  File "<pyshell#27>", line 4, in <module>
    raise MyError(e)
MyError: division by zero

если вы хотите сохранить исходный объект исключения, вы можете сделать это в своем собственном классе исключений __init__. Возможно, вы действительно захотите сохранить трассировку, поскольку сам объект исключения не предоставляет много полезной информации о том, где произошло исключение:

class MyError(Exception):
    def __init__(self, other):
        self.traceback = sys.exc_info()
        super(MyError, self).__init__(other.message)

после этого вы можете получить доступ к traceback атрибут вашего исключения, чтобы получить информацию об исходном исключении. (В Python 3 уже обеспечивает это как __traceback__ атрибут объекта исключения.)

Comments

    Ничего не найдено.