Episode 17: updates one service at a time, a health check that asks real questions, every tag pinned

updates/health.sh: 43 checks across all services (API answers, git refs, a push
message round trip, SSO redirects and token endpoint, mesh state, backup age).
updates/update.sh: per service pull or build, snapshot, recreate, wait for the
health check, put image and data back on red and stop the run.
backup/backup.sh: online dumps for n8n, Pocket ID and tinyauth; BACKUP_TAG so
pre-update snapshots are not removed by the nightly keep-daily rule.
compose.yml and caddy/Dockerfile: exact versions instead of latest, 16, 7-alpine
and caddy:2-alpine.
This commit is contained in:
Maximilian Grimm 2026-10-08 22:04:29 +02:00
parent 1655d04d7d
commit 55b2fe7646
7 changed files with 380 additions and 19 deletions

View file

@ -62,7 +62,7 @@ volumes:
services:
caddy:
image: selfhostedops/caddy:crowdsec # episode 12: caddy-ratelimit + CrowdSec bouncer + AppSec
image: selfhostedops/caddy:2.11.7-crowdsec0.14.1 # episode 12: caddy-ratelimit + CrowdSec bouncer + AppSec
build: ./caddy
restart: unless-stopped
ports:
@ -83,7 +83,7 @@ services:
networks: [proxy]
forgejo:
image: codeberg.org/forgejo/forgejo:16
image: codeberg.org/forgejo/forgejo:16.0.5
restart: unless-stopped
environment:
USER_UID: "1000"
@ -113,7 +113,7 @@ services:
networks: [proxy]
outline-postgres:
image: postgres:16-alpine
image: postgres:16.15-alpine
restart: unless-stopped
environment:
POSTGRES_USER: outline
@ -124,12 +124,12 @@ services:
networks: [internal]
outline-redis:
image: redis:7-alpine
image: redis:7.4.11-alpine
restart: unless-stopped
networks: [internal]
outline:
image: outlinewiki/outline:latest
image: outlinewiki/outline:1.10.1
restart: unless-stopped
depends_on: [outline-postgres, outline-redis]
environment:
@ -157,7 +157,7 @@ services:
networks: [proxy, internal]
vaultwarden:
image: vaultwarden/server:latest
image: vaultwarden/server:1.37.4
restart: unless-stopped
environment:
DOMAIN: https://vault.${DOMAIN}
@ -188,7 +188,7 @@ services:
networks: [proxy]
uptime-kuma:
image: louislam/uptime-kuma:1
image: louislam/uptime-kuma:2.5.5
restart: unless-stopped
volumes:
- kuma_data:/app/data
@ -197,7 +197,7 @@ services:
# Push notifications for the monitoring alerts (episode 6).
# Uptime Kuma publishes to the topic "alerts", your phone subscribes to it.
ntfy:
image: binwiederhier/ntfy:v2.28.0
image: binwiederhier/ntfy:v2.29.0
restart: unless-stopped
command: serve
environment:
@ -220,7 +220,7 @@ services:
n8n:
# Pinned. With :latest every restore from backup is silently an upgrade,
# and an upgrade is a thing you schedule, not a thing a restore does to you.
image: docker.n8n.io/n8nio/n8n:2.37.7
image: docker.n8n.io/n8nio/n8n:2.42.5
restart: unless-stopped
environment:
N8N_HOST: n8n.${DOMAIN}
@ -264,7 +264,7 @@ services:
# passkey, and switching one person off happens in one place. Pocket ID is
# small enough for a 4 GB box; groups decide who gets which service.
pocket-id:
image: ghcr.io/pocket-id/pocket-id:v2.16.0
image: ghcr.io/pocket-id/pocket-id:v2.18.0
restart: unless-stopped
environment:
APP_URL: https://id.${DOMAIN}
@ -335,7 +335,7 @@ services:
#
# Start it with: docker compose --profile agent up -d
ops-actions:
image: docker:cli
image: docker:29.8.2-cli
profiles: [agent]
restart: unless-stopped
environment: