How to handle exceptions properly in a pythonic way?

zljubisic at gmail.com zljubisic at gmail.com
Mon Nov 2 14:24:36 EST 2015


Let's say that I have the following simple function:

def get_html(url):

    wpage = requests.get(url)
    
    return wpage.text

How to handle exceptions properly that can arise during execution of the requests.get(url)?

If I call this function with

try:
    html = get_html('www.abc.com/index.html')
except ConnectionError:
        service_exception
else:
    continue_with_the_code

and ConnectionError exception happens I can handle the exception with service_exception part of the code.

I could also put some try/except block in get_html function, but the only purpose why should I do it,  is to log the url and re rise the error. Is there any other reason why should I do this?
 
def get_html(url):

    try:
        wpage = requests.get(url)
    except ConnectionError:
        flog('warning', 'ConnectionError exception', log_except=True)
        raise

    return 

Anyway, whenever I am calling the get_html function I should put it in the try/except block and handle all exceptions.
Now which exceptions? Can I know them in advance or I should wait for one to happened and then put it in caller except block?

Let's say that I have called get_html function hundred times in try/except block with ConnectionError part, and now I found a new exception that can happen during execution of the requests.get(url) command. What should I do now?
Should I put the same except block that handles that new exception in every and each of these hundred calls? 

I could also handle all exceptions in get_html function, and in case that I am not able to get the html, I can return None. 

def get_html(url):

    try:
        wpage = requests.get(url)
    except ConnectionError:
        flog('warning', 'ConnectionError exception', log_except=True)
        raise
    except Exception as e:
        flog("warning", "{0}   [wpage = requests.get(url) {1}]".format(e, url), log_except=True)
        raise
    else:

        if wpage.status_code == requests.codes.ok:
            flog('debug', 'wpage.status_code = %s' % wpage.status_code)
            html = wpage.text
        else:
            flog('debug', 'url = %s' % url)
            html = None

    return html


Now caller should only check if function has returned something other than None. Caller doesn't need try/except block anymore. Something like this:

if get_html('www.abc.com/index.html') is not None:
    I_am_sure_that_html_has_been_downloaded_correctly


Now if I want to catch a new exception, I can catch it in get_html function, which is the only change in the program.

I have read some articles that returning None is not a good approach, so I am confused.

How to handle exceptions properly in a pythonic way?

Regards.



More information about the Python-list mailing list