web.py and gunicorn

gunicorn, heroku, python, web.py

Solution

I'm afraid I'm not familar with Heroku, but I can answer your basic question.

gunicorn is a HTTP server for running Python web apps via WSGI. web.py is a framework for creating Python web apps using WSGI.

So you don't really need a tutorial for using both together, as all you need to do is figure out how to pass the WSGI entry point of your web.py application to gunicorn. A WSGI application is just a Python callable with the right interface i.e. it takes certain parameters and returns a certain response. See this WSGI tutorial for more.

The "hello world" application from the web.py tutorial looks like this test.py:

import web

urls = (
    '/', 'index'
)

class index:
    def GET(self):
        return "Hello, world!"

if __name__ == "__main__":
    app = web.application(urls, globals())
    app.run()

But that does not expose the WSGI application which gunicorn needs.

web.py provides a WSGI application via the `wsgifunc` method of `web.application`. We can add this to test.py by adding the following after the `index` class:

# For serving using any wsgi server
wsgi_app = web.application(urls, globals()).wsgifunc()

This is basically what the web.py documentation tells you to do in the deployment section, when using Apache + mod_wsgi - the fact that the Python code is the same for us with gunicorn is not a coincidence because this is exactly what WSGI gives you - a standard way to write the Python so that it can be deployed using any WSGI capable server.

As explained in the gunicorn docs, we can then point gunicorn at the `wsgi_app` member of the `test` module as follows:

(tmp)day@office:~/tmp$ gunicorn test:wsgi_app
2012-12-03 23:31:11 [19265] [INFO] Starting gunicorn 0.16.1
2012-12-03 23:31:11 [19265] [INFO] Listening at: http://127.0.0.1:8000 (19265)
2012-12-03 23:31:11 [19265] [INFO] Using worker: sync
2012-12-03 23:31:11 [19268] [INFO] Booting worker with pid: 19268

Problem

My question is basically what's in the title: how can I setup gunicorn to run a web.py app? (Also, if there are any differences, how would I do it on heroku?) I already have my app running on heroku using the built in cherrypy, but I have not been able to get gunicorn to work with web.py (I just have no idea where to start - I couldn't find any tutorials).

Original source