confusion around CustomException example in 'Python in a Nutshell'

E

erick_bodine

In Martinelli's Nutshell book in the Exceptions chapter there is an
example of a custom exception class (pg.112) that I am trying to
implement without success. The custom exception class example pulls
sys.exc_info() into an attribute and I am assuming that the attribute
would then contain the raised exception info in a tuple (admittedly I
could be assuming erroneously).

class LinuxDriverError(Exception):
def __init__(self, *args):
Exception.__init__(self, *args)
self.message = args[0]
self.wrapped_exc = sys.exc_info()

try:
raise LinuxDriverError, "raising Cain!"
except CustomException, error:
print error.message
print error.wrapped_exc

# just checking
print "sys.exc_info(): ", sys.exc_info()

If I run the above code I get the following output:

Just raising Cain!
wrapped_exc: (None, None, None)
sys.exc_info(): (<class __main__.LinuxDriverError at 0xf6f774dc>,
<__main__.LinuxDriverError instance at 0xf6f74bec>, <traceback object
at 0xf6f7193c>)

I do not understand why the wrapped_exc attribute contains no objects.

I am running 2.3.4 on a fedora core 3 box.

thanks,

erick
 
W

wittempj

I don't know the mentioned book, but if you rewrite like:.... def __init__(self, *args):
.... Exception.__init__(self, *args)
.... self.message = args[0]
....
.... def __str__(self):
.... return str(sys.exc_info())
........ raise LinuxDriverError, "raising Cain!"
........ test()
.... except LinuxDriverError, error:
.... print error
....
(<class __main__.LinuxDriverError at 0x401e305c>,
.... print "sys.exc_info(): ", sys.exc_info()

This gets what you probably expect, the way you do it there is no
traceback object when you print it
 
P

Peter Hansen

In Martinelli's Nutshell book in the Exceptions chapter there is an
example of a custom exception class (pg.112) that I am trying to
implement without success. The custom exception class example pulls
sys.exc_info() into an attribute and I am assuming that the attribute
would then contain the raised exception info in a tuple (admittedly I
could be assuming erroneously).

class LinuxDriverError(Exception):
def __init__(self, *args):
Exception.__init__(self, *args)
self.message = args[0]
self.wrapped_exc = sys.exc_info()

try:
raise LinuxDriverError, "raising Cain!"
except CustomException, error:
print error.message
print error.wrapped_exc

# just checking
print "sys.exc_info(): ", sys.exc_info()

If I run the above code I get the following output:

Just raising Cain!
wrapped_exc: (None, None, None)
sys.exc_info(): (<class __main__.LinuxDriverError at 0xf6f774dc>,
<__main__.LinuxDriverError instance at 0xf6f74bec>, <traceback object
at 0xf6f7193c>)

I do not understand why the wrapped_exc attribute contains no objects.

Because at the time you create the exception there is
no "current exception" as seen from the point of view
of sys.exc_info().

Given the way this class was written, it is clearly
intended to be raised from within an "except" statement
as a result of another exception having been caught.

Try this instead:

try:
try:
1/0
except:
raise LinuxDriverError, 'raising Cain!'
except Exception, ex:
print ex.wrapped_exc


By the way, the code you show is probably not what you
were actually running anyway... you caught a
"CustomException" but the LinuxDriverError is not
a subclass of that class so it wouldn't/shouldn't
have been caught.

-Peter
 
E

erick_bodine

Peter said:
In Martinelli's Nutshell book in the Exceptions chapter there is an
example of a custom exception class (pg.112) that I am trying to
implement without success. The custom exception class example pulls
sys.exc_info() into an attribute and I am assuming that the attribute
would then contain the raised exception info in a tuple (admittedly I
could be assuming erroneously).

class LinuxDriverError(Exception):
def __init__(self, *args):
Exception.__init__(self, *args)
self.message = args[0]
self.wrapped_exc = sys.exc_info()

try:
raise LinuxDriverError, "raising Cain!"
except CustomException, error:
print error.message
print error.wrapped_exc

# just checking
print "sys.exc_info(): ", sys.exc_info()

If I run the above code I get the following output:

Just raising Cain!
wrapped_exc: (None, None, None)
sys.exc_info(): (<class __main__.LinuxDriverError at 0xf6f774dc>,
<__main__.LinuxDriverError instance at 0xf6f74bec>, <traceback object
at 0xf6f7193c>)

I do not understand why the wrapped_exc attribute contains no
objects.

Because at the time you create the exception there is
no "current exception" as seen from the point of view
of sys.exc_info().

Given the way this class was written, it is clearly
intended to be raised from within an "except" statement
as a result of another exception having been caught.

Try this instead:

try:
try:
1/0
except:
raise LinuxDriverError, 'raising Cain!'
except Exception, ex:
print ex.wrapped_exc
This clears the fog a little.

By the way, the code you show is probably not what you
were actually running anyway... you caught a
"CustomException" but the LinuxDriverError is not
a subclass of that class so it wouldn't/shouldn't
have been caught.

<classic keyboard fumbling> What I am trying to do is get information
from a raised custom exception. I am catching the exception in a
main() function but it was actually raised in a separate module
function. It would be nice if I could print out where the exception
was raised from (module.function name + line number).

-------------------------
def some_module_function():
if something_bad:
raise LinuxDriverError, "raising.."
---------------------------

def main():
try:
mymodule.some_module_function()
except LinuxDriverError, error:
print error.message
print error.from_where



Thanks,

--Erick
 
P

Peter Hansen

<classic keyboard fumbling> What I am trying to do is get information
from a raised custom exception. I am catching the exception in a
main() function but it was actually raised in a separate module
function. It would be nice if I could print out where the exception
was raised from (module.function name + line number).

Ah, good. Exactly what the useful functions in the
'traceback' module are intended for, if I understand
your meaning...

If doing "traceback.print_exc()" is printing the
information you want (in a traceback that has much
more than what you say you want), then you can use
the other functions in that module, and methods in
the 'traceback' objects themselves (the third item
in the tuple returned by sys.exc_info()), will
give you all you could ever want...

Google can help you find examples of usage as well,
in the archives for this group.

-Peter
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,756
Messages
2,569,535
Members
45,008
Latest member
obedient dusk

Latest Threads

Top