Question

So I basically have to isolate 2 layers of the application from one another by exceptions.

I have this WLST 12c script (python 2.2), that goes like

try:
    something something...
except java.lang.UnsuportedOpperationException, (a, b):
    pass
except java.lang.reflect.UndeclaredThrowableException, (a, b):
    pass

I'd like to be able to re-raise one of my own types of exception, that contains a message about what caused the previous exception (and no, i don't know what the a and b parameters are, but i'm guessing one of them should be the exception description).

I'm a java guy myself, so i am looking forward to something like

try {
    something something...
} catch (Exception e) {
    throw new RuntimeException(e, "something horrible happened");
}
Was it helpful?

Solution

I hope I got the question right.

I'm not sure about Python 2.2 specifics, but this says you can handle exceptions the same way it's done in more recent versions:

try:
    do_stuff()
except ErrorToCatch, e:
    raise ExceptionToThrow(e)

Or maybe the last line should be raise ExceptionToThrow(str(e)). That depends on how your exception is defined. Example:

try:
    raise TypeError('foo')
except TypeError, t:
    raise ValueError(t)

This raises ValueError('foo').

Hope it helps :)

OTHER TIPS

Although this is an old post, there is a much more simple answer to the original question. To rethrow an exception after catching it, just use "raise" with no arguments. The original stack trace will be preserved.

The idiom

try:
   ...
except SomeException:
   ...
   raise

mentioned by @normaldotcom rethrows the error that has been catched as-is, without any modification. It does not answer to the OP, "How do I create a new exception that contain information about an exception that has been catched".

Indeed in some situations, one would like to create a new exception, typically to regroup many possible sources of internal errors into a single exception with a clearer message, while still keeping the traceback to the original error to enable debugging.

A way to achieve this is via the with_traceback method of BaseException. For example,

import sys

try:
  raise ValueError('internal error message')
except ValueError:
  tb = sys.exc_info()[2]
  raise Exception('new error message').with_traceback(tb)

I Python 3, the raise from construction does exactly what you ask for. It raises the new exception, saving the original exception in __cause__ attribute of the new one.

See here: https://docs.python.org/3/reference/simple_stmts.html#the-raise-statement

>>> try:
...     print(1 / 0)
... except Exception as exc:
...     raise RuntimeError("Something bad happened") from exc
...
Traceback (most recent call last):
  File "<stdin>", line 2, in <module>
ZeroDivisionError: division by zero

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

Traceback (most recent call last):
  File "<stdin>", line 4, in <module>
RuntimeError: Something bad happened
class MyException(Exception): pass

...

try:
    my_funcion(my_args)
except (IOError, KeyError, some_list_of_other_possible_exceptions), e:
    raise MyException("Uh oh")

You can extract information from the original exception, which here is bound to e, and then pass that on to your own exception when you raise it.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top