GliderJan Varho

Python hug with apache mod_wsgi

  • hug
  • Apache
  • mod_wsgi
  • Python
  • WSGI

I found it surprisingly difficult to find a plain explanation of setting up hug and apache mod_wsgi. So here is how I did it.

Minimal hug API

Writing an API with hug is really easy. You can write a "hello world" in four lines of code:

import hug

@hug.get('/hello') def hello(name: str) -> str: return "Hello " + name

Running this on a devserver is also trivial:

hug -f hello.py

mod_wsgi

Setting up mod_wsgi is not too difficult either. You need to install the module and enable it, which on Ubuntu was as easy as:

sudo apt install libapache2-mod-wsgi-py3

Note the 'py3' part, however. I wasted quite a bit of time before realizing the module uses a specific version of Python. Since hug is Python 3 only (a shame), a Python 3 build is needed.

The actual host configuration looks something like:

<VirtualHost *:80> ServerName hello.example.com DocumentRoot /var/www/hello/ WSGIDaemonProcess hello threads=1 WSGIScriptAlias / /var/www/api/hello.py

<Directory /var/www/hello> WSGIProcessGroup hello WSGIApplicationGroup %{GLOBAL} Order deny,allow Allow from all </Directory> </VirtualHost>

(This is on Ubuntu 16.04 with Apache 2.4.18, running it as the Apache user.)

The WSGI script

The WSGI entry point expected by mod_wsgi is named 'application' while hug exposes one under 'hug_wsgi'. There must be some way to change it from the above configuration (how?), but I ended up adding this to hello.py:

application = hug_wsgi

If the application was installed as a package it would be cleaner to have some kind of a separate shi like wsgi.py with just a oneliner:

from mypackage import hug_wsgi as application