From 0d0794fbf00745b534acbda89754cb8da6534bc9 Mon Sep 17 00:00:00 2001 From: Levi Neuwirth Date: Tue, 11 Aug 2026 13:49:30 +0200 Subject: [PATCH] infra: track the Forgejo compose file MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The only description of how git.levineuwirth.org is deployed lived on the VPS itself, which meant recovering the deployment required first recovering the machine — or unpacking a backup tarball to read its own compose file. It belongs with nginx/ and systemd/. Recorded in the header rather than lost to shell history: that DOMAIN, SSH_DOMAIN and ROOT_URL were placeholder text until today; that FORGEJO__* variables reach app.ini on container recreation and not on restart; that 3000 is bound to loopback on purpose; and that SSH on 2222, while genuinely open on the host, is filtered by enough public networks to be the convenience path rather than the dependable one. Also removes the caddy container and its leftovers from that box (not tracked here, but the reason belongs with this change): created at initial setup in March, never started once — it wanted host ports 80 and 443, which nginx already held. Its Caddyfile did exactly what nginx now does, and its data directories were empty. It carried restart=unless-stopped next to a stale compose backup, so the only thing it could still plausibly do was win a race for 443 against the server actually serving the site. NO_REPLY_ADDRESS is set here too, now that checking showed nothing depends on the old value: the account does not hide its email and no address in the database sits on a noreply domain, so there was no attribution to orphan. Co-Authored-By: Claude Opus 5 (1M context) Claude-Session: https://claude.ai/code/session_01SUGesXiMmACsLBTGG1xuEU --- forgejo/docker-compose.yml | 65 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 65 insertions(+) create mode 100644 forgejo/docker-compose.yml diff --git a/forgejo/docker-compose.yml b/forgejo/docker-compose.yml new file mode 100644 index 0000000..6af6c08 --- /dev/null +++ b/forgejo/docker-compose.yml @@ -0,0 +1,65 @@ +# Forgejo deployment for git.levineuwirth.org. +# +# Lives at /root/forgejo-server/docker-compose.yml on the VPS; this copy is +# the tracked source, in the same spirit as nginx/ and systemd/. Until +# August 2026 it existed only on that box, which meant the sole description +# of how the forge was deployed was inside its own backup tarball. +# +# scp forgejo/docker-compose.yml root@:/root/forgejo-server/ +# ssh root@ "cd /root/forgejo-server && docker compose up -d" +# +# Environment variables of the form FORGEJO__section__KEY are applied to +# /data/gitea/conf/app.ini by the entrypoint at startup. They take effect on +# container *recreation*, not on restart — `docker compose up -d` after an +# edit here, not `docker restart forgejo`. +# +# Notes on specific settings: +# +# DOMAIN / SSH_DOMAIN / ROOT_URL — these read git.yourdomain.com until +# 2026-08-11. nginx proxied around the mistake so the site worked, but +# Forgejo generates clone URLs, redirects, and mail links from ROOT_URL, +# so all of those were wrong. +# +# SSH_PORT 2222 — published on 0.0.0.0 and open on the host, but filtered +# by many public networks (it is unreachable from at least one Copenhagen +# library). Clone over HTTPS; treat SSH as the convenience path, not the +# dependable one. +# +# 3000 is bound to 127.0.0.1 deliberately: the web UI is reachable only +# through the host's nginx, never directly. +# +# The database is SQLite at forgejo-data/gitea/gitea.db. Backups are +# systemd/forgejo-backup.{service,timer} driving tools/forgejo-backup.sh. + +services: + forgejo: + image: codeberg.org/forgejo/forgejo:1.21.11-0 + container_name: forgejo + restart: unless-stopped + environment: + USER_UID: "1000" + USER_GID: "1000" + FORGEJO__server__DOMAIN: git.levineuwirth.org + FORGEJO__server__SSH_DOMAIN: git.levineuwirth.org + FORGEJO__server__ROOT_URL: https://git.levineuwirth.org/ + FORGEJO__server__SSH_PORT: "2222" + FORGEJO__database__DB_TYPE: sqlite3 + FORGEJO__service__DISABLE_REGISTRATION: "true" + FORGEJO__service__NO_REPLY_ADDRESS: noreply.git.levineuwirth.org + FORGEJO__actions__ENABLED: "false" + volumes: + - ./forgejo-data:/data + - /etc/localtime:/etc/localtime:ro + ports: + - "2222:22" + - "127.0.0.1:3000:3000" # Exposes web UI only to the local Nginx server + networks: + - proxy-net + security_opt: + - no-new-privileges:true + mem_limit: 512m + cpus: 1.0 + +networks: + proxy-net: + external: true