Serving Django Admin Static Assets in Production Mode

When DEBUG is disabled in Django, the framework stops serving static files automatically. This causes the admin itnerface to render without CSS and JavaScript. To resolve this, you must configure a dedicated web server to handle these assets.

Begin by updating your Django settigns:

# config/settings.py
import os
from pathlib import Path

BASE_DIR = Path(__file__).resolve().parent.parent

STATIC_URL = '/static/'
STATIC_ROOT = os.path.join(BASE_DIR, 'collected_static')

Execute the collection command to aggregate all static resources from installed applications:

cd /srv/django-project
source venv/bin/activate
python manage.py collectstatic --clear --noinput

Configure Nginx to serve the collected files directly while proxying dynamic requests to your application server:

user nginx;
worker_processes auto;
error_log /var/log/nginx/error.log warn;
pid /var/run/nginx.pid;

events {
    worker_connections 1024;
}

http {
    include /etc/nginx/mime.types;
    default_type application/octet-stream;

    log_format main '$remote_addr - $remote_user [$time_local] "$request" '
                    '$status $body_bytes_sent "$http_referer" '
                    '"$http_user_agent" "$http_x_forwarded_for"';

    server {
        listen 80;
        server_name django-app.local;

        location /static/ {
            alias /srv/django-project/collected_static/;
            expires 6M;
            access_log off;
        }

        location / {
            include uwsgi_params;
            uwsgi_pass unix:/run/uwsgi/django.sock;
            uwsgi_param Host $host;
            uwsgi_param X-Real-IP $remote_addr;
        }
    }
}

For the uWSGI application server, create a configuartion file:

# /etc/uwsgi/django.ini
[uwsgi]
chdir = /srv/django-project
module = config.wsgi:application
socket = /run/uwsgi/django.sock
chmod-socket = 660
chown-socket = nginx:nginx
processes = 4
threads = 2
master = true
vacuum = true
die-on-term = true
harakiri = 30
max-requests = 5000

Ensure the static files directory has proper permissions for the web server user. Avoid placing files under /root as the nginx process cannot access them:

mkdir -p /srv/django-project/collected_static
chown -R nginx:nginx /srv/django-project/collected_static
chmod -R 755 /srv/django-project/collected_static

Start the application server:

uwsgi --ini /etc/uwsgi/django.ini

The resulting directory structure should resemble:

/srv/django-project/
├── config/
│   ├── __init__.py
│   ├── settings.py
│   ├── urls.py
│   └── wsgi.py
├── collected_static/
│   ├── admin/
│   │   ├── css/
│   │   ├── img/
│   │   └── js/
│   └── rest_framework/
├── venv/
└── manage.py

Tags: Django static-files nginx uWSGI production-deployment

Posted on Fri, 12 Jun 2026 16:24:43 +0000 by alexanae