# DEPLOY-PRODUCAO — Runbook operacional (estado de HOJE) > 🛑 **LEIA PRIMEIRO.** Procedimento **real e executável hoje**, passo a passo, sem adivinhação. > Reflete o mecanismo atual: **a produção (VPS1) builda a si mesma** via `git pull` + `docker compose build` + `up -d`. > O fluxo-alvo (registry + deploy por tag, prod sem build) está em `deploy.md` e ainda não existe. A realidade da infra está em `arquitetura.md`. > > ⚠️ **Regra de ouro:** antes de qualquer build/deploy/push, confirme com o operador **DEV ou PRODUÇÃO**. > `dev.scoreodonto.com` = VPS4 (descartável, mas **mesmo banco** da prod). `scoreodonto.com` = VPS1 (real). > **Nunca** `git push --force` na `main`. **Dev e prod compartilham o banco** (VPS3) — o backup é a única rede de segurança. --- ## Mapa rápido (quem é quem) | Onde | Host | Papel | Socket Docker | |------|------|-------|----------------| | VPS4 | `10.99.0.4` | dev + builder (código aqui) | `/var/run/docker.sock` (root) | | VPS1 | `10.99.0.1` | produção | `unix:///run/user/1000/docker.sock` (rootless) | | VPS3 | `10.99.0.3` | Postgres + Gitea | — | - Repo: `ssh://git@10.99.0.3/ruicesar/scoreodonto.com.git` (Gitea). - Diretório do repo nas duas máquinas: `/home/deploy/stack/scoreodonto.com`. - Project Compose: `scoreodontocom` (containers `scoreodontocom-*`). --- ## FASE 0 — Pré-voo (na VPS4) ```bash cd /home/deploy/stack/scoreodonto.com # 1. Sanidade do backend node --check backend/server.js # 2. Validar a mudança em DEV (já no ar em https://dev.scoreodonto.com) # Conferir o bundle servido (deve mudar a cada rebuild): curl -s https://dev.scoreodonto.com/ | grep -oE 'index-[A-Za-z0-9_-]+\.js' | head -1 ``` ```bash # 3. BACKUP DO BANCO (rede de segurança única — dev/prod compartilham o banco) # Rodar na VPS3. Usar as credenciais do ambiente/segredo, nunca em texto puro. ssh deploy@10.99.0.3 'pg_dump -Fc scoreodonto -f /home/deploy/backups/scoreodonto_$(date +%Y%m%d_%H%M).dump' ``` --- ## FASE 1 — Versão (na VPS4) ⚠️ passo manual O bump **não é automático** (`npm run build` é só `vite build`). É preciso incrementar **à mão**: ```bash cd /home/deploy/stack/scoreodonto.com node update-version.js # incrementa o patch em frontend/constants.ts (ex.: V1.0.12 → V1.0.13) grep APP_VERSION frontend/constants.ts ``` > Hoje a versão **não fica visível no navegador** (está no bundle JS). Até a Etapa 3 (versionamento visível), anote a versão que está promovendo. --- ## FASE 2 — Commit & push para o Gitea (na VPS4) > Só execute com autorização explícita do operador (é o repo de produção). ```bash cd /home/deploy/stack/scoreodonto.com git add -A git commit -m "feat: (bump vX.Y.Z)" git push origin main ``` > ❗ Push **não** dispara deploy automático hoje (não há listener/webhook ativo). A promoção é a FASE 3. --- ## FASE 3 — Promover para produção (na VPS1) ```bash ssh deploy@10.99.0.1 export DOCKER_HOST=unix:///run/user/1000/docker.sock # docker rootless da VPS1 cd /home/deploy/stack/scoreodonto.com # 1. Trazer o código aprovado git pull origin main # 2. Carimbo de versão visível (lido pelos build args do compose) — em PROD use APP_ENV=PROD export APP_VERSION=$(grep -oE 'V[0-9]+\.[0-9]+\.[0-9]+' frontend/constants.ts | head -1) export GIT_COMMIT=$(git rev-parse --short HEAD) export BUILD_TIME=$(date -u +'%Y-%m-%d %H:%M UTC') export APP_ENV=PROD # 3. Buildar as imagens (frontend faz vite build; backend npm install) docker compose build scoreodonto-frontend scoreodonto-backend # 4. Subir (troca os containers pelas imagens novas) docker compose up -d scoreodonto-frontend scoreodonto-backend nginx ``` > Os 4 `export` carimbam versão/commit/data/ambiente na imagem. Sem eles, o build ainda funciona mas mostra `dev`/`unknown` no rodapé. Em **DEV** (VPS4) use `APP_ENV=DEV`. O backend leva ~10–30s no boot (reconecta Postgres/Dragonfly e roda as migrações idempotentes). --- ## FASE 4 — Verificação pós-deploy (na VPS1) ```bash export DOCKER_HOST=unix:///run/user/1000/docker.sock # Containers no ar docker ps --format '{{.Names}} | {{.Status}}' | grep score # Backend: esperar a linha de migração + carimbo de versão docker logs scoreodontocom-scoreodonto-backend-1 --tail 40 | grep -iE 'migration|VERSION' # alvo: [MIGRATION] all migrations OK # [VERSION] ScoreOdonto API vX.Y.Z · commit ... · build ... · PROD # Confirmar a versão no ar SEM acessar container (a forma definitiva): curl -s https://scoreodonto.com/api/version # {"name":"ScoreOdonto API","version":"vX.Y.Z","commit":"...","build":"...","environment":"PROD"} # E visualmente: a versão aparece no rodapé do menu lateral (Sidebar). ``` **Smoke tests mínimos:** abrir `https://scoreodonto.com`, logar, e exercitar o que mudou (ex.: lançamento financeiro, agenda, salas). Conferir ausência de erro 500 no `docker logs`. --- ## FASE 5 — Rollback (se algo quebrar) As migrações são **aditivas** → reverter o **código** é seguro (colunas/tabelas extras ficam inertes). ```bash ssh deploy@10.99.0.1 export DOCKER_HOST=unix:///run/user/1000/docker.sock cd /home/deploy/stack/scoreodonto.com git log --oneline -5 # achar o commit bom anterior git checkout # ou: git reset --hard docker compose build scoreodonto-frontend scoreodonto-backend docker compose up -d scoreodonto-frontend scoreodonto-backend ``` > Hoje o rollback **rebuilda** a versão anterior (as imagens são `:latest`, não há tag por versão). Quando a **Etapa 6** entregar deploy por tag + registry, o rollback vira só `docker compose pull` da tag anterior — sem rebuild. Restaurar o dump do banco (FASE 0) só em caso extremo: > `pg_restore -d "postgresql://scoreodonto_user:@10.99.0.3:5432/scoreodonto" --clean .dump` --- ## Resumo em uma tela ``` VPS4: validar em dev → node --check → backup do banco (VPS3) → node update-version.js → commit → git push origin main (com OK do operador) VPS1: git pull → docker compose build → docker compose up -d → verificar logs ([MIGRATION] all migrations OK) + smoke test Rollback: git checkout → build → up -d ```