Dec. 10, 2019, 10 p.m.

Test deployment of a django app with uwsgi and lighttpd

CAUTION

I do not recommend the following deployment procedures in a production environment, please read and understand the Reference section of this post.

Prerequisites

Git, python3 virtual env and your preferred terminal (Shell).

sudo apt install git python3-virtualenv

I also recommend setting up different user to run the django uwsgi.

Procedures

Open shell, Clone the django project using git and change directory.

Check settings.py and configure necessary parameters.

Set up the virtual environment and install the required packages:

$ python3 -m venv myvenv

$ source myvenv/bin/activate

$ python3 -m pip install -r requirements.txt

Configure superuser account:

$ python3 manage.py createsuperuser

Test if the django app works

$ python3 manage.py runserver 0.0.0.0:8080

Visit your localhost:8080 or from another PC (make sure that ALLOWED_HOSTS is configured in your settings.py)

Install and configure uWSGI

$ python3 -m pip install uwsgi --user

$ nano uwsgi.py

Sample configuration:

The directory where our django app is at: /var/www/django/

The django project name is mysite

Static files will be served from var/www/django/static and var/www/django/media

[uwsgi]
chdir=/var/www/django/
module=mysite.wsgi:application
DJANGO_SETTINGS_MODULE=mysite.settings
master=True
pidfile=/tmp/project-master.pid
vacuum=True
max-requests=1000
#daemonize=/var/log/uwsgi/yourproject.log
http=127.0.0.1:8000
processes=3
hakariki=20
max-requests=3000
home=/var/www/django/myvenv/

static-map = /static=/var/www/django/static/
static-map = /upload=/var/www/django/media/

Test if it runs, execute uwsgi: uwsgi --ini ./uwsgi.ini

Sample output:

[uWSGI] getting INI configuration from ./uwsgi.ini
*** Starting uWSGI 2.0.18 (32bit) on [Tue Dec 10 20:44:39 2019] ***
compiled with version: 8.3.0 on 16 July 2019 12:06:45
os: Linux-4.19.75-v7+ #1270 SMP Tue Sep 24 18:45:11 BST 2019
nodename: Pi
machine: armv7l
clock source: unix
pcre jit disabled
detected number of CPU cores: 4
current working directory: /var/www/
writing pidfile to /tmp/project-master.pid
detected binary path: /home/pi/.local/bin/uwsgi
chdir() to  /var/www/django
your processes number limit is 8732
your memory page size is 5120 bytes
detected max file descriptor number: 2048
lock engine: pthread robust mutexes
thunder lock: disabled (you can enable it with --thunder-lock)
uwsgi socket 0 bound to TCP address 127.0.0.1:8000 fd 3
Python version: 3.7.3 (default, Apr  3 2019, 05:39:12)  [GCC 8.2.0]
...
WSGI app 0 (mountpoint='') ready in 2 seconds on interpreter 0x12a71b8 pid: 5916 (default app)
*** uWSGI is running in multiple interpreter mode ***
spawned uWSGI master process (pid: 5916)
spawned uWSGI worker 1 (pid: 5917, cores: 1)
spawned uWSGI worker 2 (pid: 5918, cores: 1)
spawned uWSGI worker 3 (pid: 5919, cores: 1)
spawned uWSGI http 1 (pid: 5920)
...

Lighttpd configuration (/etc/lighttpd/external.conf)

server.modules = (
    "mod_proxy"
)

 $SERVER["socket"] == "0.0.0.0:80" {
  server.document-root = "/var/www/"
    proxy.server = (
        "" => (
            (
                "host" => "127.0.0.1",
                "port" => 8000
            )
        )
    )
}

Start lighttpd and check if it works, visit http://yourip

References

https://docs.djangoproject.com/en/2.2/howto/deployment/wsgi/uwsgi/

https://uwsgi-docs.readthedocs.io/en/latest/Lighttpd.html

https://docs.djangoproject.com/en/2.2/howto/static-files/deployment/

https://uwsgi-docs.readthedocs.io/en/latest/StaticFiles.html

https://lincolnloop.com/blog/serving-static-files-uwsgi/

https://uwsgi-docs.readthedocs.io/en/latest/tutorials/Django_and_nginx.html

https://uwsgi-docs.readthedocs.io/en/latest/Lighttpd.html