# Первичная настройка stage-сервера (88.204.171.93)

**Разовая процедура.** После этого деплой происходит автоматически на каждый push в `main`.

## Текущее состояние сервера (проверено)

- Ubuntu 24.04.3, 4 CPU, 15 ГБ RAM (8 ГБ свободно)
- **Диск 19 ГБ, свободно 4 ГБ** ← узкое место, нужно следить
- Docker 28.2.2 установлен ✓
- PostgreSQL 14/16 на 5432 (используется существующими приложениями)
- Порты 80/443 заняты legacy nginx
- Порты 5000, 5002, 5005 заняты legacy .NET (food-market-server, calcman, makesales)
- SSH: `nns@88.204.171.93:9393`

## Шаг 1 — выдать nns доступ к Docker (ОДНОРАЗОВО)

На сервере:
```bash
ssh -p 9393 nns@88.204.171.93
sudo usermod -aG docker nns
exit
```

**Важно:** после этой команды разлогинься из SSH и залогинься снова — групповые права применяются только при новой сессии.

Проверь:
```bash
ssh -p 9393 nns@88.204.171.93 'docker ps'
```
Должно выдать список контейнеров (сейчас пустой) без permission denied.

## Шаг 2 — задать пароль для stage postgres

Генерим рандомный 32-символьный пароль и кладём его в GitHub Secrets:
```bash
# На твоём Mac
PASS=$(openssl rand -base64 24 | tr -d '=+/' | head -c 32)
gh secret set STAGE_POSTGRES_PASSWORD --repo nurdotnet/food-market --body "$PASS"
# Сохрани его же в файл на всякий случай:
echo "POSTGRES_PASSWORD=$PASS" > ~/.food-market-secrets/stage-postgres.env
chmod 600 ~/.food-market-secrets/stage-postgres.env
```

## Шаг 3 — проверить порты

Наш stage слушает:
- **8080** — API (health: `curl http://88.204.171.93:8080/health`)
- **8081** — Web (SPA с reverse-proxy на API)
- **5434** — Postgres (только localhost, не наружу)

Проверь что эти порты ещё не заняты:
```bash
ssh -p 9393 nns@88.204.171.93 'ss -tlnp | grep -E "(8080|8081|5434)"'
```
Если пусто — всё ок.

## Шаг 4 — первый ручной деплой (для проверки)

После того как GitHub Actions собрал образы (это происходит автоматически при пуше), запусти workflow вручную:
```bash
gh workflow run deploy-stage.yml --repo nurdotnet/food-market
# Смотри статус:
gh run watch --repo nurdotnet/food-market
```

После успеха откроется: http://88.204.171.93:8081 — это stage-админка.

## Мониторинг диска

Добавь cron на stage-сервере:
```bash
ssh -p 9393 nns@88.204.171.93
crontab -e
```
Добавить строку:
```
0 */6 * * * /usr/bin/df -h / | awk '/\/$/ {if ($5+0 > 85) system("curl -sS -X POST https://api.telegram.org/bot$TG_TOKEN/sendMessage --data-urlencode chat_id=$TG_CHAT --data-urlencode text=\"Disk on stage: "$5" used\"")}'
```
(Подставь реальные TG_TOKEN и TG_CHAT, или используй `source ~/.food-market-secrets/telegram.env` в cron-wrapper.)

## Что происходит при каждом push в main

```
push → Github Actions:
  1. CI (backend build + web build) — если упал, Telegram "CI FAILED"
  2. Docker Images (api + web → ghcr.io) — если упал, Telegram "CI FAILED"
  3. Deploy stage (после успешного Docker) →
       ssh nns@stage → docker compose pull → up -d → curl /health
       Если успешно — Telegram "Deploy stage OK — SHA — http://..."
       Если упало — Telegram "Deploy stage FAILED — ссылка на лог"
```

Ты видишь уведомление в Telegram, открываешь stage, проверяешь, говоришь «мёрджим в prod» или «откатывай».
