Python exception chaining [duplicate]
Solution 1:
Exception chaining is only available in Python 3, where you can write:
try:
v = {}['a']
except KeyError as e:
raise ValueError('failed') from e
which yields an output like
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
In most cases, you don't even need the from
; Python 3 will by default show all exceptions that occured during exception handling, like this:
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
What you can do in Python 2 is adding custom attributes to your exception class, like:
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)
Solution 2:
Is this what you're asking for?
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
If you want to store the original exception object, you can certainly do so in your own exception class's __init__
. You might actually want to store the traceback as the exception object itself doesn't provide much useful information about where the exception occurred:
class MyError(Exception):
def __init__(self, other):
self.traceback = sys.exc_info()
super(MyError, self).__init__(other.message)
After this you can access the traceback
attribute of your exception to get info about the original exception. (Python 3 already provides this as the __traceback__
attribute of an exception object.)