feat(deploy): deploy por tag na produção (Etapa 6)
build-and-push / build (push) Successful in 1m6s

- docker-compose.prod.yml: produção roda imagens versionadas do registry (sem build)
- deploy-prod.sh <tag>: pull da tag + up -d --no-build + verificação /api/version + rollback
- deploy.md: Metade A (CI) marcada como FEITA

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
VPS 4 Builder
2026-06-16 09:25:27 +02:00
parent 914ebc9dbf
commit fc0d65fde0
3 changed files with 68 additions and 5 deletions
Executable
+47
View File
@@ -0,0 +1,47 @@
#!/usr/bin/env bash
# =============================================================================
# Deploy por TAG na PRODUÇÃO (VPS1) — Etapa 6
# Puxa a imagem versionada do registry do Gitea e sobe, SEM build.
#
# Uso (NA VPS1): ./deploy-prod.sh v1.0.13
# Rollback: ./deploy-prod.sh <tag-anterior>
#
# Pré-requisitos (uma vez): docker login git.clube67.com (token read:package).
# =============================================================================
set -euo pipefail
TAG="${1:-}"
if [ -z "$TAG" ]; then
echo "uso: ./deploy-prod.sh <vX.Y.Z> (ex.: ./deploy-prod.sh v1.0.13)"
echo "tags disponíveis no registry: veja git.clube67.com → Packages"
exit 1
fi
export DOCKER_HOST=unix:///run/user/1000/docker.sock
export SCOREODONTO_TAG="$TAG"
cd "$(dirname "$0")"
FILES="-f docker-compose.yml -f docker-compose.prod.yml"
echo "──────────────────────────────────────────────────────────────"
echo " Deploy ScoreOdonto → PRODUÇÃO tag: $TAG"
echo "──────────────────────────────────────────────────────────────"
echo "⚠️ Recomendado: backup do banco antes (dev/prod compartilham o banco):"
echo " ssh deploy@10.99.0.3 'pg_dump -Fc scoreodonto -f ~/backups/scoreodonto_\$(date +%Y%m%d_%H%M).dump'"
echo
echo "[1/3] pull das imagens $TAG ..."
docker compose $FILES pull scoreodonto-backend scoreodonto-frontend
echo "[2/3] subindo (sem build) ..."
docker compose $FILES up -d --no-build scoreodonto-backend scoreodonto-frontend nginx
echo "[3/3] verificação (aguardando boot do backend) ..."
sleep 12
echo -n " versão no ar: "
curl -s --max-time 10 https://scoreodonto.com/api/version || echo "(ainda subindo — confira em alguns segundos)"
echo
docker logs scoreodontocom-scoreodonto-backend-1 --tail 5 2>&1 | grep -iE 'VERSION|MIGRATION' || true
echo
echo "✅ Deploy concluído (tag $TAG)."
echo " Rollback: ./deploy-prod.sh <tag-anterior>"
+14
View File
@@ -0,0 +1,14 @@
# Override de PRODUÇÃO (VPS1): roda IMAGENS VERSIONADAS do registry em vez de buildar.
# A produção não builda — só consome a imagem pronta publicada pela CI (Etapa 5).
#
# Uso (na VPS1), via deploy-prod.sh <tag>, que faz:
# SCOREODONTO_TAG=v1.0.13 docker compose -f docker-compose.yml -f docker-compose.prod.yml pull ...
# docker compose -f docker-compose.yml -f docker-compose.prod.yml up -d --no-build ...
#
# O --no-build garante que o build: do compose base seja ignorado (usa a imagem puxada).
services:
scoreodonto-backend:
image: git.clube67.com/ruicesar/scoreodonto-backend:${SCOREODONTO_TAG:-latest}
scoreodonto-frontend:
image: git.clube67.com/ruicesar/scoreodonto-frontend:${SCOREODONTO_TAG:-latest}
+7 -5
View File
@@ -38,13 +38,15 @@
## 3. As duas metades do fluxo
### Metade A — Integração contínua (push → imagem) 🔜
### Metade A — Integração contínua (push → imagem) ✅ FEITO
1. Desenvolvedor trabalha na VPS4 e valida em `https://dev.scoreodonto.com`.
2. `git push origin main` para o Gitea (VPS3).
3. A **CI do Gitea** (Gitea Actions) builda a imagem Docker (frontend multi-stage + backend), injetando **versão semântica, commit curto e data de build**.
4. A imagem é enviada ao **Registry privado da VPS3** com tags como `:main`, `:<commit-curto>`.
2. `git push origin main` (ou tag `v*`) para o Gitea (VPS3).
3. A **CI do Gitea** (Gitea Actions) builda backend+frontend via `docker compose build`, injetando **versão, commit curto e data de build** (build args → `VITE_*`/`process.env`).
4. As imagens são enviadas ao **Container Registry do Gitea** com tags `:<versão>`, `:<commit-curto>` e `:latest`.
5. **Nada vai para produção aqui.** Esta metade só produz e guarda o artefato.
> **Implementado em 16/jun/2026.** Workflow: `.gitea/workflows/build.yml`. Runner: `vps4-builder` (act_runner 0.6.1, **modo host** com Docker, serviço systemd `act_runner` na VPS4, label `self-hosted`). Login no registry usa o secret `REGISTRY_TOKEN` se presente, senão a credencial do host. Validado: push na main → build → `scoreodonto-{backend,frontend}:v1.0.13`/`:<commit>`/`:latest` publicados.
### Metade B — Entrega por tag (tag → produção) 🔜
1. Quando uma versão está aprovada, cria-se uma **tag semântica**: `git tag v1.0.15 && git push origin v1.0.15`.
2. A CI marca a imagem correspondente como `:v1.0.15` no registry (promoção do artefato já testado — sem rebuild).
@@ -94,7 +96,7 @@ Visível no **rodapé** da aplicação, em um **endpoint de diagnóstico** (ex.:
|-------|---------|--------|
| 3 | Versionamento visível (rodapé + endpoint + log) | ✅ |
| 4 | Registry Docker privado na VPS3 | ✅ (Gitea Container Registry — ver `REGISTRY.md`) |
| 5 | Pipeline de build no Gitea (push → imagem → registry), **sem deploy** | 🔜 |
| 5 | Pipeline de build no Gitea (push → imagem → registry), **sem deploy** | ✅ (`.gitea/workflows/build.yml` + runner `vps4-builder`) |
| 6 | Deploy por TAG (`vX.Y.Z` → produção na VPS1) + rollback por imagem | 🔜 |
Quando as Etapas 36 estiverem prontas, este documento deixa de ter marcações 🔜 e passa a descrever o fluxo corrente.