开发者

Best practice for handling exceptions from libraries imported by other libraries in Python?

What is the appropriate way for handling exceptions from libraries imported by other libraries in Python?

For example, I have a library called "pycontrol" that I import into my main program. "pycontrol" imports the "suds" library. The "suds" library, in turn, imports the "urllib2" library. I've noticed that when the "suds" library has trouble connecting to remote resources it is accessing through "urllib2," these exceptions trickle up to my main program.

My best guess at this point is to import urllib2 and suds into my global name space and catch typical exceptions that get thrown by them and aren't handled in "pycontrol".

Is there some other best practice as to how one might approach this?

A basic idea of what the snippet of code looks like (without importing suds or urllib2 into global name space):

    import pycontrol.pycontrol as pc

    print "Connecting to iControl API on LTM %s..." % ltm
    try:
        b = pc.BIGIP(hostname=ltm, username=user, password=pw, 
            wsdls=wsdl_list, fromurl=True,
            debug=soap_debug)
    except (<whattocatch>), detail:
        print "Error: could not connect to iControl API on LTM %s... aborting!" % ltm
        print "Details: %s" % detail
        exitcode = 1
    else:
        print "Connection successfully established."

Here's a sample traceback:

Connecting to iControl API on LTM s0-bigip1-lb2.lab.zynga.com...
Traceback (most recent call last):
  File "./register.py", line 507, in <module>
    main()
  File "./register.py", line 415, in main
    b = build_bigip_object(ltm, user, pw, WSDLS, soap_debug = False)
  File "./register.py", line 85, in build_bigip_object
    debug=soap_debug)
  File "build/bdist.macosx-10.6-universal/egg/pycontrol/pycontrol.py", line 81, in __init__
  File "build/bdist.macosx-10.6-universal/egg/pycontrol/pycontrol.py", line 103, in _get_clients
  File "build/bdist.macosx-10.6-universal/egg/pycontrol/pycontrol.py", line 149, in _get_suds_client
  File "/Library/Python/2.6/site-packages/suds/client.py", line 111, in __init__
    self.wsdl = reader.open(url)
  File "/Library/Python/2.6/site-packages/suds/reader.py", line 136, in open
    d = self.fn(url, self.options)
  File "/Library/Python/2.6/site-packages/suds/wsdl.py", line 136, in __init__
    d = reader.open(url)
  File "/Library/Python/2.6/site-packages/suds/reader.py", line 73, in open
    d = self.download(url)
  File "/Library/Python/2.6/site-packages/suds/reader.py", line 88, in download
    fp = self.options.transport.open(Request(url))
  File "/Library/Python/2.6/site-packages/suds/transport/https.py", line 60, in open
    return  HttpTransport.open(self, request)
  File "/Library/Python/2.6/site-packages/suds/transport/http.py", line 62, in open
    return self.u2open(u2request)
  File "/Library/Python/2.6/site-packages/suds/transport/http.py", line 118, in u2open
    return url.open(u2request, timeout=tm)
  File "/System/Library/Frameworks/Python.framework/Versions/2.6/lib/python2.6/urllib2.py", line 383, in open
    response = self._open(req, data)
  File "/System/Library/Frameworks/Python.framework/Versions/2.6/lib/python2.6/urllib2.py", line 401, in _open
    '_open', req)
  File "/System/Library/Frameworks/Python.framework/Versions/2.6/lib/python2.6/urllib2.py", line 361, in _call_chain
    result = func(*args)
  File "/System/Library/Frameworks/Python.framework/Versions/2.6/lib/python2.6/urllib2.py", line 1138, in https_open
    return self.do_open(httplib.HTTPSConnection, req)
  File "/System/Library/Frameworks/Python.framework/Versions/2.6/lib/python2.6/urllib2.py", line 1105, in do_open
    raise URLError(err)开发者_StackOverflow中文版
urllib2.URLError: <urlopen error [Errno 8] nodename nor servname provided, or not known>


I think you answered you question yourself. Import urllib2 and catch the exception in your module.

from urllib2 import URLError

try:
    # something
except URLError, e:
    # Do something in case of error.


Why do you need to catch specific exceptions at all? After all, any exception (not only URLError) raised from b = pc.BIGIP(...) means you cannot go on.

I suggest:

import traceback

try:
    b = pc.BIGIP(...)
except:
    traceback.print_exc()
    exitcode = 1
else:
    do_something_with_connection(b)

Another idea: Why bother with catching the exception at all? The Python interpreter will dump a stack trace to stderr and exit the program when it encounters an unhandled exception:

b = bc.BIGIP(...)
do_something_with_connection(b)

Or if you need to write to an error log:

import logging
import sys

def main():
   b = bc.BIGIP(...)
   do_something_with_connection(b)

if __name__ == "__main__":
    try:
        main()
    except:
        logging.exception("An unexpected error occured")
        sys.exit(1)
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜