Развертывание Django проекта на NGINX в Ubuntu (uWSGI + MariaDB)
Развёртывание Django-приложения разбивается на два этапа:
- Установка и настройка среды Python и uWSGI;
- Настройка веб-сервера NGINX.
Дополнительно рассмотрим подключение к MariaDB/MySQL.
Python, Django и uWSGI
apt-get install nginx uwsgi python3 uwsgi-plugin-python3 python3-pip python3-dev build-essential libssl-dev libffi-dev python3-setuptools
pip3 install virtualenv uwsgi django
Создаём каталоги для статики и медиа:
mkdir -p /var/www/my_app/static /var/www/my_app/media
chown www-data.www-data /var/www/my_app/media
chown www-data.www-data /var/www/my_app/static
Копируем приложение в /var/www/my_app. Примерная структура:
/var/www/my_app/
|-- app1
| |-- __init__.py
| |-- admin.py
| |-- apps.py
| |-- migrations/
| |-- models.py
| |-- static/
| |-- templates/
| |-- urls.py
| |-- views.py
|-- my_app
| |-- __init__.py
| |-- asgi.py
| |-- settings.py
| |-- urls.py
| |-- wsgi.py
|-- manage.py
|-- db.sqlite3
Правим настройки проекта:
vi /var/www/my_app/my_app/settings.py
ALLOWED_HOSTS = ['www.example.com']
DATABASES = {
'default': {
# ...
}
}
STATIC_ROOT = '/var/www/my_app/static'
MEDIA_ROOT = '/var/www/my_app/media'
где:
ALLOWED_HOSTS— разрешённые доменные имена сайта;DATABASES— подключение к базе данных;STATIC_ROOT/MEDIA_ROOT— каталоги статики и пользовательских файлов.
Собираем статику:
cd /var/www/my_app
python3 manage.py collectstatic
Настраиваем uWSGI:
vi /etc/uwsgi/apps-enabled/my_app.ini
[uwsgi]
chdir = /var/www/my_app
env = DJANGO_SETTINGS_MODULE=my_app.settings
wsgi-file = my_app/wsgi.py
max-requests = 5000
plugins = python3
processes = 5
threads = 2
master = true
die-on-term = true
socket = /run/uwsgi/my_app.sock
chmod-socket = 660
vacuum = true
uid = www-data
gid = www-data
где:
chdir— каталог проекта;env— модуль настроек Django;wsgi-file— путь доwsgi.py;processes/threads— воркеры;socket— сокет для связи с NGINX;uid/gid— пользователь процесса.
Исправлены опечатки оригинала: gui → gid, chdir без ведущего слеша.
systemctl restart uwsgi
Настройка NGINX
vi /etc/nginx/conf.d/my_app.conf
server {
listen 80;
server_tokens off;
server_name my_app my_app.domain.local;
location / {
include uwsgi_params;
uwsgi_pass unix:/run/uwsgi/my_app.sock;
}
location /static/ {
alias /var/www/my_app/static/;
}
location /media/ {
alias /var/www/my_app/media/;
}
}
systemctl restart nginx
Подключение к базе данных MariaDB/MySQL
MariaDB
apt-get install mariadb-server
systemctl enable mariadb
mysqladmin -u root password
Django требует кодировку UTF-8. Правим конфигурацию клиента:
vi /etc/mysql/mariadb.conf.d/50-client.cnf
[mysql]
...
default-character-set = utf8mb4
vi /etc/mysql/mariadb.conf.d/50-mysql-clients.cnf
[mysql]
...
default-character-set = utf8mb4
Современная рекомендация — utf8mb4 (полный Unicode, включая эмодзи); utf8 в MySQL/MariaDB — это 3-байтовый вариант.
vi /etc/mysql/mariadb.conf.d/50-server.cnf
character-set-server = utf8mb4
collation_server = utf8mb4_unicode_ci
systemctl restart mariadb
Подготовка базы данных
Создайте базу, пользователя и выдайте права (см. инструкции по созданию БД и настройке прав).
Модуль для Python
apt-get install libmysqlclient-dev
pip3 install mysqlclient
Первая команда — библиотеки для сборки, вторая — клиент MySQL для Python.
Настройка подключения
vi /var/www/my_app/my_app/settings.py
Меняем sqlite на MySQL:
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.mysql',
'NAME': 'database_name',
'HOST': 'localhost',
'USER': 'db_user',
'PASSWORD': 'db_password',
'OPTIONS': {'charset': 'utf8mb4'},
}
}
где:
NAME— имя базы;HOST— сервер БД;USER— пользователь с правами на базу;PASSWORD— пароль пользователя.
Проверка выборки
from django.db import connection
cursor = connection.cursor()
cursor.execute("SELECT * FROM users")
print(cursor.fetchall())
Пример извлекает всё содержимое таблицы users и выводит на экран.
Тонкости и подводные камни
utf8vsutf8mb4— для полного Unicode (эмодзи, редкие символы) используйтеutf8mb4.- Сокет uWSGI — путь в
uwsgi.iniиuwsgi_passв NGINX должны совпадать. uid/gid— в оригинальной инструкции была опечаткаgui; правильный параметр —gid.collectstatic— запускать после измененияSTATIC_ROOT; статику отдаёт NGINX, а не Django.ALLOWED_HOSTS— при обращении по IP или другому домену добавьте его, иначе 400 Bad Request.mysqlclient— требует заголовков MySQL; при ошибках сборки ставьтеdefault-libmysqlclient-devилиpkg-config.uwsgi-plugin-python3— обязателен, иначе uWSGI не запустит Python-приложение.- Права на media —
www-dataдолжен иметь запись, иначе загрузка файлов упадёт.
Шпаргалка
apt-get install nginx uwsgi python3 uwsgi-plugin-python3 python3-pip python3-dev build-essential
pip3 install virtualenv uwsgi django mysqlclient
mkdir -p /var/www/my_app/{static,media}
# settings.py: ALLOWED_HOSTS, DATABASES, STATIC_ROOT, MEDIA_ROOT
python3 manage.py collectstatic
# /etc/uwsgi/apps-enabled/my_app.ini -> socket, chdir, wsgi-file
# /etc/nginx/conf.d/my_app.conf -> uwsgi_pass unix:/run/uwsgi/my_app.sock
systemctl restart uwsgi nginx
Проверено на: Ubuntu 22.04/24.04 + Django 5, uWSGI, MariaDB 10.11+.
Дата: Сентябрь 2026.