--- name: deploy description: Ship the colectivo stack to ambrosio (https://erosi.limonia.net) with pre-deploy DB backup, or roll back code + DB to a previous deploy. Trigger when the user asks to deploy, ship, push to prod, roll back, or undo a deploy. --- # Deploy + rollback skill Deploys and rollbacks for the production stack on ambrosio. **Every deploy takes a paired DB backup first**, every successful deploy is logged with `(timestamp, git-sha, backup-filename)`, and rollback uses that log to restore both code and DB atomically. ## Trigger Use this skill when the user says any of: - "deploy", "deploy to ambrosio", "deploy to prod", "ship it" - "roll back", "rollback", "undo the deploy", "revert prod" - "list deploys", "what was the last deploy" ## What the skill does ### Forward (deploy) 1. **`just deploy`** runs `infra/scripts/deploy-erosi.sh`: - Captures the local short SHA (`git rev-parse --short HEAD`). - rsyncs the working tree to `ambrosio:/opt/colectivo/` (excludes `.git`, `node_modules`, `**/.env`, etc.). - On a fresh `.env`, generates secrets and bails — operator fills `PUBLIC_KEYCLOAK_URL` + `KEYCLOAK_CLIENT_SECRET` and re-runs. - **Pre-deploy DB backup**: `pg_dumpall` from the prod `db` container → `backups/predeploy--.sql.gz` on ambrosio. Aborts the deploy if the dump is < 1 KiB. Keeps the newest 10 backups. - Rebuilds the `app` image with `GIT_SHA` build-arg (so `__APP_COMMIT__` lands in the bundle, Fase 14.3). - `docker compose up -d` brings the stack to the new image. - Applies any pending DB migrations. - On success, appends `\t\t` to `/opt/colectivo/.deploys.log`. 2. Site smoke: `curl -I https://erosi.limonia.net/` should return 200. ### Reverse (rollback) 1. **`just rollback-list`** prints recent rows from `.deploys.log` so the user can pick a target. 2. **`just rollback`** rolls back code + DB to the previous deploy (last but one line of `.deploys.log`). 3. **`just rollback-to `** rolls back to a specific deploy. 4. **`just rollback-code`** rolls back code only, leaves the DB at current state — useful when the regression is UI-only and the DB schema is compatible. `infra/scripts/rollback-erosi.sh` enforces: - Confirms with a 5-second abort window before doing anything destructive. - Verifies the target SHA is reachable locally (`git cat-file -e`) and that the backup file still exists on ambrosio. - Materialises the target commit into a temporary `git worktree`, rsyncs from there, never disturbs the user's working tree. - Stops `app / auth / rest / realtime / storage` before the DB restore so they don't observe inconsistent state. - `gunzip | psql -v ON_ERROR_STOP=1` restores the dump. - Rebuilds the app image at the rolled-back SHA and brings the stack up. - **Does not** write a new `.deploys.log` line — rollback is intentionally not a deploy event. ## Safety boundaries - The stack lives on ambrosio. The external proxy + TLS terminator are off-stack (`docs/deployment.md`). Neither this skill nor the scripts ever touch host TLS or the external proxy. - `infra/scripts/deploy-erosi.sh` never runs `sudo`. - `--no-verify` / `--amend` are never used. Pre-commit hooks must pass. - Always confirm with the user before invoking `just rollback*` — DB restore is destructive and irreversible. - Storage volume (`/var/lib/storage`, user uploads) is **not** part of the rollback. Treated as append-only. ## What to tell the user Before running anything: - Show the local short SHA + branch + remote. - For deploy: confirm with the user. Mention "this will take a fresh DB backup before deploying." - For rollback: show `just rollback-list` output, ask which SHA, confirm destructive nature. After running: - Print the new `.deploys.log` tail (or the rollback target). - Curl-probe the site and report. ## Files this skill touches - `infra/scripts/deploy-erosi.sh` — deploy, with pre-deploy backup + .deploys.log writing. - `infra/scripts/rollback-erosi.sh` — rollback, paired code + DB. - `Justfile` — `deploy`, `rollback`, `rollback-list`, `rollback-to`, `rollback-code` recipes. - `docs/deployment.md` — runbook for both flows. ## Anti-trigger If the user is just asking *what would happen* on deploy (status, dry-run-style questions), DO NOT run anything. Answer from the script content.