Two of Serverpod's own conventions, as its v4 project template and roles have them. CI now runs `serverpod generate` (CLI pinned to the server's Serverpod version, like the template's workflow) and fails if the committed generated code differs from its output, so a model or endpoint changed without regenerating can't reach main. Checked in a clean clone: today's code passes, a committed stale generated file fails. redeploy.sh now applies the migrations in a run of their own, with Serverpod's maintenance role (--role=maintenance --apply-migrations), after the dump and before switching to the new server. That run exits with 0 only if the migrations worked, and each migration is one transaction, so a failing one stops the deploy while the old server keeps serving; before, the new server applied them at start and would have crash-looped. Tested on the local stack: a deploy through the new step, and a failing run (wrong database password) that exits with 1 after six attempts. AGENTS.md says migrations must keep the old server working until the switch. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Signed-off-by: Tizian 「ティツィアーン」 <raisondetredev@pm.me>
83 lines
3 KiB
YAML
83 lines
3 KiB
YAML
# The Halkyon Learn instance: Caddy in front, the Serverpod server, PostgreSQL.
|
|
#
|
|
# cd deploy
|
|
# cp .env.example .env && chmod 600 .env # then fill in the secrets
|
|
# docker compose up -d --build
|
|
#
|
|
# Only Caddy publishes ports. Docker opens published ports directly in the kernel's
|
|
# packet filter, past ufw, and the Serverpod server listens on every interface, so the
|
|
# server and Postgres publish nothing: they're reachable only inside this project's
|
|
# network, where Caddy finds the server by its service name.
|
|
|
|
name: halkyon-learn
|
|
|
|
# Logs go to the host's journal, whose size and age limits apply (journald.conf).
|
|
x-logging: &logging
|
|
driver: journald
|
|
|
|
services:
|
|
caddy:
|
|
image: caddy:2
|
|
restart: unless-stopped
|
|
ports:
|
|
- "80:80"
|
|
- "443:443"
|
|
- "443:443/udp" # HTTP/3
|
|
environment:
|
|
# `learn.halkyon.eu` on sahaquiel (automatic Let's Encrypt certificate);
|
|
# `http://localhost` for the local rehearsal (plain HTTP, no certificate).
|
|
DOMAIN: ${DOMAIN:?set DOMAIN in deploy/.env}
|
|
volumes:
|
|
- ./Caddyfile:/etc/caddy/Caddyfile:ro
|
|
- caddy_data:/data # certificates: must survive restarts (rate limits)
|
|
- caddy_config:/config
|
|
depends_on:
|
|
- server
|
|
logging: *logging
|
|
|
|
server:
|
|
build:
|
|
context: ..
|
|
dockerfile: halkyon_learn_server/Dockerfile
|
|
image: halkyon-learn-server
|
|
restart: unless-stopped
|
|
# Applies pending migrations at every start, then serves. One instance only, so
|
|
# no two servers ever migrate at once. (On learn.halkyon.eu, deploy/redeploy.sh has
|
|
# applied them in a run of their own before, so nothing is left to do here.)
|
|
command: ["--apply-migrations"]
|
|
environment:
|
|
SERVERPOD_DATABASE_PASSWORD: ${POSTGRES_PASSWORD:?set POSTGRES_PASSWORD in deploy/.env}
|
|
SERVERPOD_PASSWORD_serverSideSessionKeyHashPepper: ${SESSION_KEY_HASH_PEPPER:?set SESSION_KEY_HASH_PEPPER in deploy/.env}
|
|
# GitHub sign-in, only with this instance's GitHub OAuth app; empty: off.
|
|
SERVERPOD_PASSWORD_githubClientId: ${GITHUB_CLIENT_ID:-}
|
|
SERVERPOD_PASSWORD_githubClientSecret: ${GITHUB_CLIENT_SECRET:-}
|
|
# Where the source of what this instance runs is; empty: the project's.
|
|
SOURCE_URL: ${SOURCE_URL:-}
|
|
depends_on:
|
|
postgres:
|
|
condition: service_healthy
|
|
logging: *logging
|
|
|
|
postgres:
|
|
image: postgres:16
|
|
restart: unless-stopped
|
|
# The server's session is UTC anyway (the driver sets it); this makes the
|
|
# database's own default UTC too, for psql, COPY loads and future sidecars.
|
|
command: ["postgres", "-c", "timezone=UTC", "-c", "log_timezone=UTC"]
|
|
environment:
|
|
POSTGRES_USER: halkyon_learn
|
|
POSTGRES_DB: halkyon_learn
|
|
POSTGRES_PASSWORD: ${POSTGRES_PASSWORD:?set POSTGRES_PASSWORD in deploy/.env}
|
|
volumes:
|
|
- postgres_data:/var/lib/postgresql/data
|
|
healthcheck:
|
|
test: ["CMD-SHELL", "pg_isready -U halkyon_learn -d halkyon_learn"]
|
|
interval: 5s
|
|
timeout: 5s
|
|
retries: 12
|
|
logging: *logging
|
|
|
|
volumes:
|
|
caddy_data:
|
|
caddy_config:
|
|
postgres_data:
|