z19r

Cute little WSGI error handling pattern

Here's a cute little pattern I threw together when writing sixpack. I'm assuming you're using Werkzeug, but you could do the same thing with Flask, or pure WSGI.

First step is to write a little decorator that you're going to decorate your route handlers with. It's pretty straight forward. Here I used the decorator package to simplify things, but you can just do it in pure python if you don't need the additional dependency.

import decorator
from redis import ConnectionError

@decorator.decorator
def service_unavailable_on_connection_error(f, *args, **kwargs):
try:
    return f(*args, **kwargs)
except ConnectionError:
    return json_error({"message": "redis is not available"}, None, 503)

It's simply going to try to run the method you decorated, and catch a Redis ConnectionError. You could do this for any datastore, or anything else that's prone to complete failure. In this example, json_error() is a simple helper method that returns a JSON response with the correct Content-Type, status, etc. headers.

Then, in your server you can have something like this:

def __init__(self, redis_conn):
    self.redis = redis_conn

    self.url_map = Map([
        Rule('/_status', endpoint='status'),
    ])

... more werkzeug boilerplate

@service_unavailable_on_connection_error
def on_status(self, request):
    self.redis.ping()
    return json_success({'version': __version__}, request)

If self.redis.ping() throws ConnectionError the decorator will catch it, and return the failing JSON. So, like the title says, nothing groundbreaking, but cute and might save you a few lines.

comments powered by Disqus