Введение
Django – один из наиболее популярных веб-фреймворков, позволяющий создавать веб-приложения различной сложности. Django включает в себя упрощенный веб-сервер для тестирования кода в процессе разработки, однако для запуска готового приложения в продуктовой среде рекомендуется использовать более безопасный веб-сервер.
В данной статье мы рассмотрим установку и конфигурацию, достаточную для разворачивания Django-приложения. В качестве ОС будем использовать Ubuntu 24.04, для конфигурации будет использоваться пользователь, отличный от root с sudo-привилегиями. Вместо стандартной SQLite будет использован PostgreSQL, для запуска приложения будет использоваться Gunicorn, в качестве веб-сервера и реверс-прокси – Nginx.
Установка необходимых пакетов
Для запуска сервера с Django в первую очередь нам потребуется установить требуемые зависимости из репозиториев Ubuntu. Для этого обновим индексы пакетов, после чего загрузим и установим следующие пакеты:
sudo apt update
sudo apt install python3-pip python3-dev python3-venv libpq-dev postgresql postgresql-contrib nginx
В результате выполнения команд будет установлен менеджер пакетов pip и необходимые зависимости для сборки пакетов Python, а также веб-сервер Nginx. На данном этапе мы можем приступить к настройке окружения нашего сервера с Django с пакетами Python.
Создание базы данных и пользователя PostgreSQL
При создании БД вы можете настроить базу данных самостоятельно либо использовать нашу облачную базу данных – в таком случае самостоятельно администрировать и конфигурировать ее вам не потребуется. Преимущества облачной базы данных включают в себя:
- разделение общей нагрузки между сервером приложения и сервером базы данных;
- простоту масштабирования;
- снижение расходов на поддержку инфраструктуры;
- производительность и безопасность.
Подробно процесс создания и настройки облачной БД PostgreSQL описан в нашем руководстве. Создать базу данных вы можете в разделе “Облако”.
Создание и настройка БД самостоятельно
Для создания БД самостоятельно нам потребуется дополнительно установить пакеты Postgresql и нужные ей библиотеки из репозиториев Ubuntu командой:
sudo apt install postgresql postgresql-contrib
По умолчанию для локальных подключений Postgres позволяет использовать БД без дополнительной аутентификации, если имя пользователя системы совпадает с существующим пользователем Postgres.
В процессе установки PostgreSQL автоматически создается пользователь ОС postgres
, а также соответствующий пользователь PostgreSQL с правами администратора. Для входа в интерактивную сессию Postgres используем команду sudo
с соответствующим именем пользователя:
sudo -u postgres psql
В результате выполнения команды откроется консоль PostgreSQL. Создадим базу данных и пользователя для нее:
CREATE DATABASE myproject;
CREATE USER myprojectuser WITH PASSWORD 'password';
Далее изменим некоторые настройки для данного пользователя, что несколько ускорит операции с базой данных, поскольку корректные значения не потребуется выставлять при каждом запросе. В качестве стандартной кодировки выставим UTF-8, поскольку это кодировка, ожидаемая Django. В качестве часового пояса установим UTC, в качестве схемы изоляции транзакций – “read committed”. Данные настройки соответствуют рекомендованным в документации Django.
ALTER ROLE myprojectuser SET client_encoding TO 'utf8';
ALTER ROLE myprojectuser SET default_transaction_isolation TO 'read committed';
ALTER ROLE myprojectuser SET timezone TO 'UTC';
После чего выдадим права администратора для созданной БД нашему пользователю, а также сделаем его владельцем БД:
GRANT ALL PRIVILEGES ON DATABASE myproject TO myprojectuser;
ALTER DATABASE myproject OWNER TO myprojectuser;
Для выхода из консоли PostgreSQL введите команду:
\q
Создание виртуального окружения Python для Django
Следующим шагом в настройке нашего сервера с Django является создание виртуального окружения. В качестве директории проекта будет использоваться директория myproject в домашней директории нашего пользователя. Создадим и перейдем в нее:
mkdir ~/myproject
cd ~/myproject
Для создания виртуального окружения воспользуемся модулем venv
, встроенным в Python:
python3 -m venv myprojectenv
Активируем виртуальное окружение и установим необходимые модули:
source myprojectenv/bin/activate
pip install django gunicorn psycopg2
pip install -r requirements.txt
в директории, содержащей файл.Создание проекта и его настройка
После подготовки виртуального окружения создадим наш проект командой django-admin
:
django-admin startproject myproject ~/myproject
После выполнения команды структура проекта будет иметь следующий вид:
~/myproject/
├── manage.py - скрипт для управления проектом
├── myproject/ - директория с файлами проекта
│ ├── asgi.py
│ ├── __init__.py
│ ├── settings.py - файл настроек проекта
│ ├── urls.py
│ └── wsgi.py
└── myprojectenv/ - директория с виртуальным окружением
Настройка проекта
Для редактирования настроек проекта откройте файл settings.py
в любом удобном вам текстовом редакторе:
vim ~/myproject/myproject/settings.py
На строке, следующей за импортом pathlib
, добавьте импорт os
:
from pathlib import Path
import os
Затем нам потребуется внести домен и/или IP вашего сервера в разрешенные. Для этого отредактируйте директиву ALLOWED_HOSTS
, внеся все необходимые значения в массив:
ALLOWED_HOSTS = ['example.com', '203.0.113.5']
Далее потребуется скорректировать настройки подключения к базе данных. Для этого в файле найдите раздел DATABASES
и отредактируйте его следующим образом:
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.postgresql_psycopg2',
'NAME': 'myproject',
'USER': 'myprojectuser',
'PASSWORD': 'password',
'HOST': 'localhost',
'PORT': '',
}
}
В поле NAME
укажите название БД, в поле USER
– созданного ранее пользователя, в поле PASSWORD
– указанный при создании пользователя пароль.
После настройки БД внесем настройку для сборки статических файлов в одну директорию. Для этого добавьте директиву STATIC_ROOT
, например, после директивы STATIC_URL
:
STATIC_URL = '/static/'
STATIC_ROOT = os.path.join(BASE_DIR, 'static/')
После чего сохраните файл и закройте текстовый редактор.
Завершение процесса настройки локального сервера с Django
На данном этапе мы можем мигрировать схему нашей БД, используя скрипт manage.py
:
~/myproject/manage.py makemigrations
~/myproject/manage.py migrate
После завершения миграции создайте аккаунт администратора:
~/myproject/manage.py createsuperuser
Вам потребуется указать имя пользователя, адрес электронной почты создаваемого администратора и пароль.
Также соберем статический контент в указанную ранее в конфиге директорию:
~/myproject/manage.py collectstatic
После подтверждения операции статика будет собрана в директорию static
внутри проекта.
Если на вашем сервере установлен firewall, временно внесите в исключения 8000 порт для проверки работы сайта:
sudo ufw allow 8000
Для запуска тестового сервера выполните команду:
~/myproject/manage.py runserver 0.0.0.0:8000
В браузере откройте домен/IP вашего сервера с портом 8000
http://server_domain_or_IP:8000
Должна открыться стартовая страница Django:

Также рекомендуем проверить работу админ-панели, добавив /admin
в конец URL. На открывшейся странице введите логин и пароль пользователя, созданного ранее, и нажмите Log in:

После авторизации должна открыться стандартная админ-панель:

После проверки остановите тестовый веб-сервер, нажав CTRL+C
в терминале.
Проверка работы Gunicorn
Перед выходом из виртуального окружения протестируем Gunicorn – нам необходимо убедиться, что приложение успешно запускается. Для этого в директории проекта (в нашем случае ~/myproject
) выполните команду:
gunicorn --bind 0.0.0.0:8000 myproject.wsgi
Команда запустит Gunicorn на том же интерфейсе, что и тестовый сервер ранее.
Для запуска Gunicorn используется синтаксис модулей Python – в данном случае был указан относительный путь до файла wsgi.py
в модуле myproject
. После завершения проверки работы сайта нажмите CTRL+C
в терминале для остановки веб-сервера.
Создание и запуск Gunicorn с помощью сервиса systemd
Для запуска Gunicorn в рамках данной статьи будет использоваться сервис systemd
, однако это не единственный возможный способ – если вам данный способ не подходит, вы можете ознакомиться с альтернативами в документации Gunicorn.
Создадим файл сервиса командой:
sudo vim /etc/systemd/system/gunicorn.service
Содержимое файла должно быть примерно следующим:
[Unit]
Description=gunicorn daemon
After=network.target
[Service]
User=beget
Group=www-data
WorkingDirectory=/home/beget/myproject
ExecStart=/home/beget/myproject/myprojectenv/bin/gunicorn --access-logfile - --workers 3 --bind unix:/home/beget/myproject/myproject.sock myproject.wsgi:application
[Install]
WantedBy=multi-user.target
В файле необходимо изменить:
- В поле
User
вместоbeget
укажите имя пользователя, созданного при настройке сервера. - В
WorkingDirectory
измените путь на соответствующий директории вашего проекта. - В
ExecStart
также скорректируйте путь до исполняемого файла Gunicorn и файла сокета, а также укажите нужные вам настройки Gunicorn – например, можно изменить количество воркеров с 3 на другое.
После чего сохраните файл. Теперь можно запустить сервер командой:
sudo systemctl enable --now gunicorn
Проверка работы сервиса systemd
Для проверки статуса выполните команду, в выводе будет отображаться, запустился ли сервис:
sudo systemctl status gunicorn
Затем проверьте наличие файла сокета в директории проекта:
ls -la ~/myproject | grep sock
Ожидаемый вывод:
srwxrwxrwx 1 beget www-data 0 May 28 15:19 myproject.sock
Если команда проверки статуса сообщает, что сервис не смог запуститься (Active: dead) или файл сокета в директории отсутствует, проверьте логи Gunicorn командой:
sudo journalctl -u gunicorn
В логах сервиса найдите текст ошибки. Причин в данном случае может быть несколько:
- Владельцем файлов проекта является
root
вместо созданного вами пользователя. В таком случае измените владельца командой chown. - Пути в файле сервиса не ведут в нужную директорию. Убедитесь, что:
- Путь в директиве
WorkingDirectory
ведет в директорию проекта. - Путь до исполняемого файла Gunicorn в
ExecStart
указывает на путь, содержащий в себе путь до виртуального окружения +/bin/gunicorn
. - Путь до файла сокета содержит путь до директории проекта + название файла сокета.
- Путь до wsgi-файла указан корректно в соответствии с синтаксисом модулей Python.
- Путь в директиве
После внесения изменений в /etc/systemd/system/gunicorn.service
выполните команды:
sudo systemctl daemon-reload
sudo systemctl restart gunicorn
Убедитесь, что сервис успешно запускается перед тем, как продолжить настройку.
Настройка Nginx в качестве реверс-прокси к Gunicorn
После того как Gunicorn успешно настроен, нам необходимо настроить Nginx для проксирования трафика процессу. Для начала создадим файл конфигурации в /etc/nginx/sites-available
:
sudo vim /etc/nginx/sites-available/myproject
В файле добавим блок сервера:
server {
listen 80;
server_name server_domain_or_IP;
location = /favicon.ico { access_log off; log_not_found off; }
location /static/ {
root /home/beget/myproject;
}
location / {
include proxy_params;
proxy_pass http://unix:/home/beget/myproject/myproject.sock;
}
}
В конфигурации задаем 80 порт для прослушивания, в server_name
указываем домен/IP сервера, по которому будет доступен наш Django-проект. Создаем location
для favicon.ico
– для него отключаем логирование в access.log
. После чего добавляем location
для статических файлов – в нашем случае /static/
, в качестве корневой указываем директорию проекта. Также нам необходимо добавить location /
– здесь мы настраиваем проксирование на созданный gunicorn-сокет. Все пути должны быть скорректированы с учетом используемого вами имени пользователя и директории проекта. После чего сохраните файл и закройте редактор.
Для того чтобы активировать конфиг для Nginx, создайте символьную ссылку на него в директории /etc/nginx/sites-enabled
:
sudo ln -s /etc/nginx/sites-available/myproject /etc/nginx/sites-enabled
После чего проверьте конфиг nginx на предмет синтаксических ошибок:
sudo nginx -t
Если при проверке обнаружены ошибки, откройте файл в /etc/nginx/sites-available
и устраните их. Если ошибок нет, перезагрузите nginx командой:
sudo systemctl restart nginx
Также нам необходимо закрыть порт 8000, который мы открывали ранее, и открыть 80 порт на firewall. Для этого выполните команды:
sudo ufw delete allow 8000
sudo ufw allow 'Nginx Full'
После чего проверьте работу сайта по домену/IP сервера – сайт должен быть доступен.
Часто возникающие ошибки
Вместо приложения отображается стандартная заглушка Nginx
Стандартная страница Nginx будет отображаться, если для домена/IP, по которому совершается обращение к серверу, нет соответствующего конфигурационного файла. Nginx использует блоки server_name
для того чтобы определить, как ответить на тот или иной запрос. В данном случае вам необходимо проверить блок server_name
в конфигурационном файле, созданном для вашего проекта, на предмет опечаток в доменном имени или IP-адресе.
При открытии сайта отображается 502 код ответа
502 код ответа говорит о том, что Nginx не может успешно проксировать запрос. Причин подобного поведения может быть много – чтобы локализовать ошибку, проверим логи ошибок Nginx командой:
sudo tail -F /var/log/nginx/error.log
После чего выполним запрос к сайту – в логах должна появиться свежая ошибка. Часто возникающие варианты ошибок:
connect() to unix:/home/beget/myproject/myproject.sock failed (2: No such file or directory)
Данная ошибка говорит о том, что nginx не мог найти файл сокета gunicorn по указанному в конфигу пути. В данном случае рекомендуем проверить корректность указанного в конфиге пути. Если указанный путь корректен, возможно, gunicorn не может создать файл сокета. В таком случае необходимо произвести диагностику gunicorn, как описано в соответствующем разделе данной статьи.
connect() to unix:/home/beget/myproject/myproject.sock failed (13: Permission denied)
Данная ошибка означает, что Nginx не смог подключиться к сокету gunicorn из-за недостатка прав на чтение либо исполнение. Для диагностики проблемы необходимо проверить соответствующие права на всём пути от корневой директории до файла сокета. Для проверки можно воспользоваться командой:
namei -nom /home/beget/myproject/myproject.sock
Пример вывода с ошибкой в правах:
f: /home/beget/myproject/myproject.sock
drwxr-xr-x root root /
drwxr-xr-x root root home
drwxr-x--- beget beget beget
drwxrwxr-x beget beget myproject
srwxrwxrwx beget www-data myproject.sock
В данном случае ошибка возникает из-за того, что у директории beget не выставлены права на чтение для пользователей, не являющихся владельцем файла и не находящихся в группе владельца (последние 3 – в drwxr-x---
). Для исправления ошибки воспользуемся командой:
sudo chmod 755 /home/beget
После исправления прав вывод namei
будет отображаться следующим образом:
f: /home/beget/myproject/myproject.sock
drwxr-xr-x root root /
drwxr-xr-x root root home
drwxr-xr-x beget beget beget
drwxr-xr-x beget beget myproject
srwxrwxrwx beget www-data myproject.sock
Django выводит ошибку “could not connect to server: Connection refused”
Одна из ошибок, которые могут возникать на части страниц Django, может иметь следующий вид:
OperationalError at /admin/login/
could not connect to server: Connection refused
Is the server running on host "localhost" (127.0.0.1) and accepting
TCP/IP connections on port 5432?
Данная ошибка говорит о том, что Django не может успешно подключиться к базе данных Postgres. Убедитесь, что сервис базы данных запущен командой:
sudo systemctl status postgresql
Если сервис не запущен, включите и запустите его командой:
sudo systemctl enable --now postgresql
Если после запуска ошибка всё еще будет возникать, убедитесь, что в файле настроек сервера с Django (~/myproject/myproject/settings.py
) указаны корректные доступы к базе данных.
Дальнейшая диагностика
Для дальнейшей диагностики приложения рекомендуем проверить логи сервисов. Вам могут быть полезны следующие:
- Логи процессов nginx:
sudo journalctl -u nginx
- Логи запросов nginx:
/var/log/nginx/access.log
- Логи ошибок nginx:
/var/log/nginx/error.log
- Логи работы Gunicorn:
sudo journalctl -u gunicorn
После обновления конфигурации или самого приложения вероятнее всего вам потребуется перезапустить процессы сервисов для того, чтобы они вступили в силу.
Если вы вносите изменения в код приложения Django, перезапустите процесс Gunicorn командой:
sudo systemctl restart gunicorn
Если вы вносите изменения в файл сервиса systemd gunicorn, перезапустите демон и сам процесс:
sudo systemctl daemon-reload
sudo systemctl restart gunicorn
Если вы вносите изменения в конфигурацию nginx, проверьте корректность синтаксиса конфига командой:
sudo nginx -t
И если ошибок нет, перезапустите nginx:
sudo systemctl restart nginx
Заключение
В данной статье мы рассмотрели развертывание Django. Рассказали, как использовать Django, Nginx и Gunicorn и подключить Postgresql к Django, разобрали создание и настройку веб-приложения Django в виртуальном окружении и конфигурацию Gunicorn для запуска приложения. Также мы настроили Nginx в качестве реверс-прокси для обработки внешних подключений и их передачи Gunicorn и отдачи статического контента.
Django упрощает создание проектов и приложений, предоставляя большое количество готовых компонентов, позволяя сфокусироваться на разработке собственного решения.
Если возникнут вопросы, напишите нам, пожалуйста, тикет из панели управления аккаунта (раздел “Помощь и поддержка”), а если вы захотите обсудить эту статью, хостинг для Django, наши продукты или свой проект с коллегами по цеху и сотрудниками Бегета – ждем вас в нашем сообществе в Telegram.