Files
social-graph/deploy/social.deepfishing.ru.md
T
gitrusprusandCursor 10e7d65a00 Fix production auth by proxying /api to backend in remote builds.
Remote frontend nginx now forwards API requests to Django so login and registration work when the host proxy only routes to port 8080.

Co-authored-by: Cursor <cursoragent@cursor.com>
2026-06-29 09:33:54 +03:00

11 KiB
Raw Blame History

Развёртывание Social Graph на social.deepfishing.ru

Инструкция для production-сервера social.deepfishing.ru. Приложение публикуется через Docker; снаружи доступен только веб-прокси (80/443).

Адрес приложения: https://social.deepfishing.ru


Схема

https://social.deepfishing.ru (:443)
        ↓
Прокси на хосте (Apache или nginx)
        ↓
┌───────────────────────────────────────┐
│  frontend-контейнер (nginx)          │
│  127.0.0.1:8080 → SPA + статика      │
└───────────────────────────────────────┘
        ↓  (режим remote)
┌───────────────────────────────────────┐
│  backend-контейнер (gunicorn)         │
│  127.0.0.1:8000 → Django API          │
│  SQLite в Docker volume               │
└───────────────────────────────────────┘
Режим Где данные Backend
local IndexedDB в браузере не нужен
remote SQLite на сервере обязателен

Для social.deepfishing.ru рекомендуется remote + USE_JWT_AUTH=true (регистрация, вход, общая база).


1. Требования

  • Linux (Ubuntu 22.04+ / Debian 12+)
  • Docker Engine + Docker Compose
  • Git
  • DNS: запись A (или AAAA) social.deepfishing.ru → IP сервера
  • Apache2 или nginx на хосте

Установка Docker:

curl -fsSL https://get.docker.com | sh
sudo usermod -aG docker "$USER"
# перелогиньтесь
docker compose version

2. Клонирование

sudo mkdir -p /opt/social-graph
sudo chown "$USER:$USER" /opt/social-graph
git clone <URL-репозитория> /opt/social-graph
cd /opt/social-graph
git checkout main

3. Конфигурация deploy/.env.prod

cd /opt/social-graph
cp deploy/.env.prod.example deploy/.env.prod
nano deploy/.env.prod

Рекомендуемый конфиг для social.deepfishing.ru (remote)

VITE_DATA_MODE=remote

FRONTEND_BIND=127.0.0.1
FRONTEND_PORT=8080
BACKEND_BIND=127.0.0.1
BACKEND_PORT=8000

DJANGO_SECRET_KEY=<сгенерируйте-длинную-случайную-строку>
ALLOWED_HOSTS=social.deepfishing.ru
USE_JWT_AUTH=true

Сгенерировать DJANGO_SECRET_KEY:

python3 -c "import secrets; print(secrets.token_urlsafe(50))"

Альтернатива — только UI (local)

Если backend не нужен, данные останутся в браузере каждого пользователя:

VITE_DATA_MODE=local
FRONTEND_BIND=127.0.0.1
FRONTEND_PORT=8080

Файл deploy/.env.prod не коммитить.


4. Запуск контейнеров

cd /opt/social-graph

Remote (frontend + backend)

Обязательно: VITE_DATA_MODE=remote в .env.prod и профиль with-backend — иначе вход/регистрация не работают (ошибка 405).

docker compose -f docker-compose.prod.yml --env-file deploy/.env.prod build
docker compose -f docker-compose.prod.yml --env-file deploy/.env.prod --profile with-backend up -d --build

Команда поднимает оба контейнера. Frontend в remote-сборке проксирует /api → backend внутри Docker.

Только frontend (local)

docker compose -f docker-compose.prod.yml --env-file deploy/.env.prod up -d --build frontend

Проверка на сервере

docker compose -f docker-compose.prod.yml ps
curl -s -o /dev/null -w "frontend: %{http_code}\n" http://127.0.0.1:8080/
curl -s -o /dev/null -w "backend:  %{http_code}\n" http://127.0.0.1:8000/api/v1/meta/choices/
curl -s -o /dev/null -w "public:   %{http_code}\n" https://social.deepfishing.ru/

Логи:

docker logs sg_frontend --tail 50
docker logs sg_backend --tail 50

Перед prod-запуском остановите dev-контейнеры: docker compose down


5. Прокси на хосте

Контейнеры слушают только 127.0.0.1. Снаружи — прокси на 80/443.

Apache2

sudo apt install apache2
sudo a2enmod proxy proxy_http headers rewrite ssl
sudo cp deploy/apache/social-graph.conf /etc/apache2/sites-available/social-graph.conf
sudo nano /etc/apache2/sites-available/social-graph.conf

Пример VirtualHost:

<VirtualHost *:80>
    ServerName social.deepfishing.ru

    ProxyPreserveHost On
    RequestHeader set X-Forwarded-Proto "https"
    RequestHeader set X-Forwarded-For %{REMOTE_ADDR}s

    # API (режим remote)
    ProxyPass        /api http://127.0.0.1:8000/api
    ProxyPassReverse /api http://127.0.0.1:8000/api

    # Frontend SPA
    ProxyPass        / http://127.0.0.1:8080/
    ProxyPassReverse / http://127.0.0.1:8080/

    ErrorLog ${APACHE_LOG_DIR}/social-graph-error.log
    CustomLog ${APACHE_LOG_DIR}/social-graph-access.log combined
</VirtualHost>
sudo a2ensite social-graph.conf
sudo a2dissite 000-default.conf
sudo apache2ctl configtest
sudo systemctl reload apache2

HTTPS (Let's Encrypt):

sudo apt install certbot python3-certbot-apache
sudo certbot --apache -d social.deepfishing.ru

После certbot сайт будет доступен по https://social.deepfishing.ru .

nginx на хосте

sudo apt install nginx
sudo nano /etc/nginx/sites-available/social-graph
server {
    listen 80;
    server_name social.deepfishing.ru;

    location /api/ {
        proxy_pass http://127.0.0.1:8000/api/;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Proto $scheme;
    }

    location / {
        proxy_pass http://127.0.0.1:8080;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Proto $scheme;
    }
}
sudo ln -s /etc/nginx/sites-available/social-graph /etc/nginx/sites-enabled/
sudo nginx -t
sudo systemctl reload nginx
sudo certbot --nginx -d social.deepfishing.ru

6. Первый вход

  1. Откройте https://social.deepfishing.ru
  2. Регистрация: https://social.deepfishing.ru/register
  3. Или вход: https://social.deepfishing.ru/login

Если на сервере есть пользователь legacy (данные после миграции), задайте пароль:

cd /opt/social-graph
docker compose -f docker-compose.prod.yml --profile with-backend exec backend python manage.py shell
from django.contrib.auth import get_user_model
User = get_user_model()
u = User.objects.get(username='legacy')
u.set_password('ваш-надёжный-пароль')
u.save()
exit()

Вход: https://social.deepfishing.ru/login → логин legacy.


7. Обновление

cd /opt/social-graph
git pull

docker compose -f docker-compose.prod.yml --env-file deploy/.env.prod up -d --build frontend
docker compose -f docker-compose.prod.yml --env-file deploy/.env.prod --profile with-backend up -d --build backend

sudo systemctl reload apache2   # или: sudo nginx -s reload

Проверка: https://social.deepfishing.ru


8. Резервное копирование

cd /opt/social-graph
docker compose -f docker-compose.prod.yml --profile with-backend exec backend \
  python manage.py dumpdata contacts --indent 2 \
  > backup-social-deepfishing-$(date +%F).json

Копия SQLite (backend должен быть остановлен):

docker compose -f docker-compose.prod.yml --profile with-backend stop backend
docker run --rm -v social-graph_sqlite_data:/data -v "$PWD":/backup alpine \
  cp /data/db.sqlite3 /backup/db-social-deepfishing-$(date +%F).sqlite3
docker compose -f docker-compose.prod.yml --profile with-backend start backend

9. Безопасность

sudo ufw allow OpenSSH
sudo ufw allow 'Apache Full'   # или 'Nginx Full'
sudo ufw enable
Порт Доступ
443, 80 открыт (прокси)
8080, 8000 только 127.0.0.1

10. Устранение неполадок

Симптом Решение
405 Not Allowed при входе/регистрации Запросы /api попали во frontend вместо backend. Пересоберите с VITE_DATA_MODE=remote (в образе включится nginx.remote.conf) и поднимите backend: --profile with-backend
502 на https://social.deepfishing.ru docker ps, логи sg_frontend / sg_backend
Страница открывается, API 404 Backend не запущен или нет прокси /api
401 / не пускает USE_JWT_AUTH=true в .env.prod, пересобрать backend
Данные не сохраняются между устройствами VITE_DATA_MODE=remote, пересобрать frontend
Белый экран docker logs sg_frontend, пересборка с --build
cd /opt/social-graph
docker compose -f docker-compose.prod.yml --env-file deploy/.env.prod ps
docker logs sg_frontend --tail 100
docker logs sg_backend --tail 100
docker compose -f docker-compose.prod.yml --profile with-backend exec backend python manage.py migrate

11. Шпаргалка (social.deepfishing.ru, remote)

cd /opt/social-graph
cp deploy/.env.prod.example deploy/.env.prod
# ALLOWED_HOSTS=social.deepfishing.ru
# VITE_DATA_MODE=remote
# USE_JWT_AUTH=true
# DJANGO_SECRET_KEY=...

docker compose -f docker-compose.prod.yml --env-file deploy/.env.prod build
docker compose -f docker-compose.prod.yml --env-file deploy/.env.prod up -d --build frontend
docker compose -f docker-compose.prod.yml --env-file deploy/.env.prod --profile with-backend up -d --build backend

# Apache: ServerName social.deepfishing.ru
# ProxyPass /api → 127.0.0.1:8000
# ProxyPass /    → 127.0.0.1:8080
# certbot --apache -d social.deepfishing.ru

Проверка: https://social.deepfishing.ru