mirror of
https://github.com/aarmea/fahrengit-451.git
synced 2026-03-22 08:58:15 +00:00
Change written by Claude Code: ❯ Consider the geofencing rules defined at <config/geo_rules.yml> and consumed by <geoblock_watcher/watcher.py>. Make it so that you can pass in an HTML file response instead of a short plain text body. For this exercise, you may assume that the entire contents of the HTML (HTML, CSS, JS, image resources) will be included inline in the file. You may have to modify the <docker-compose.yml> to provide a new (read-only) bind-mount for these files.
128 lines
4.5 KiB
YAML
128 lines
4.5 KiB
YAML
services:
|
|
|
|
# ── Forgejo ────────────────────────────────────────────────────────────────
|
|
forgejo:
|
|
image: codeberg.org/forgejo/forgejo:9
|
|
container_name: forgejo
|
|
restart: unless-stopped
|
|
environment:
|
|
- USER_UID=1000
|
|
- USER_GID=1000
|
|
- FORGEJO__server__DOMAIN=${DOMAIN}
|
|
- FORGEJO__server__ROOT_URL=https://${DOMAIN}/
|
|
- FORGEJO__server__HTTP_PORT=3000
|
|
- FORGEJO__server__DISABLE_SSH=true
|
|
- FORGEJO__service__DISABLE_REGISTRATION=${DISABLE_REGISTRATION:-true}
|
|
- FORGEJO__database__DB_TYPE=sqlite3
|
|
- FORGEJO__database__PATH=/data/gitea/forgejo.db
|
|
- FORGEJO__log__LEVEL=Info
|
|
volumes:
|
|
- forgejo_data:/data
|
|
- /etc/timezone:/etc/timezone:ro
|
|
- /etc/localtime:/etc/localtime:ro
|
|
networks:
|
|
- internal
|
|
healthcheck:
|
|
test: ["CMD", "wget", "-qO-", "http://localhost:3000/api/healthz"]
|
|
interval: 30s
|
|
timeout: 5s
|
|
retries: 3
|
|
|
|
# ── nginx (reverse proxy + GeoIP blocking) ─────────────────────────────────
|
|
nginx:
|
|
build:
|
|
context: ./nginx
|
|
dockerfile: Dockerfile
|
|
container_name: nginx
|
|
restart: unless-stopped
|
|
ports:
|
|
- "80:80"
|
|
- "443:443"
|
|
volumes:
|
|
# NOTE: conf.d is intentionally NOT mounted from the host — the nginx
|
|
# Docker entrypoint renders templates/git.conf.template into conf.d at
|
|
# container start, substituting ${DOMAIN}. Mounting conf.d from the host
|
|
# would shadow that rendered output and break the virtual host.
|
|
- ./nginx/geoblock:/etc/nginx/geoblock:ro # rendered by geoblock_watcher
|
|
- ./config/geoblock_pages:/etc/nginx/geoblock_pages:ro # HTML block pages
|
|
- ./certs/live:/etc/letsencrypt/live:ro
|
|
- ./certs/archive:/etc/letsencrypt/archive:ro
|
|
- ./certs/options-ssl-nginx.conf:/etc/letsencrypt/options-ssl-nginx.conf:ro
|
|
- ./certs/ssl-dhparams.pem:/etc/letsencrypt/ssl-dhparams.pem:ro
|
|
- certbot_webroot:/var/www/certbot:ro
|
|
- geoip_db:/usr/share/GeoIP:ro
|
|
- nginx_logs:/var/log/nginx
|
|
networks:
|
|
- internal
|
|
depends_on:
|
|
- forgejo
|
|
environment:
|
|
- DOMAIN=${DOMAIN}
|
|
healthcheck:
|
|
test: ["CMD", "nginx", "-t"]
|
|
interval: 60s
|
|
timeout: 5s
|
|
retries: 3
|
|
|
|
# ── MaxMind GeoIP database updater ────────────────────────────────────────
|
|
geoipupdate:
|
|
image: ghcr.io/maxmind/geoipupdate:v7
|
|
container_name: geoipupdate
|
|
restart: unless-stopped
|
|
environment:
|
|
- GEOIPUPDATE_ACCOUNT_ID=${MAXMIND_ACCOUNT_ID}
|
|
- GEOIPUPDATE_LICENSE_KEY=${MAXMIND_LICENSE_KEY}
|
|
- GEOIPUPDATE_EDITION_IDS=GeoLite2-City
|
|
- GEOIPUPDATE_FREQUENCY=72 # hours — MaxMind updates twice a week
|
|
- GEOIPUPDATE_DB_DIR=/usr/share/GeoIP
|
|
volumes:
|
|
- geoip_db:/usr/share/GeoIP
|
|
networks:
|
|
- internal
|
|
|
|
# ── Geo-block config watcher ───────────────────────────────────────────────
|
|
# Watches geo_rules.yml; re-renders the nginx map snippet and reloads nginx
|
|
# whenever rules change.
|
|
geoblock_watcher:
|
|
build:
|
|
context: ./geoblock_watcher
|
|
dockerfile: Dockerfile
|
|
container_name: geoblock_watcher
|
|
restart: unless-stopped
|
|
volumes:
|
|
- ./config:/app/host:ro
|
|
- ./config/geoblock_pages:/app/geoblock_pages:ro # HTML block pages (validation)
|
|
- ./nginx/geoblock:/app/geoblock # shared with nginx (rw here)
|
|
- /var/run/docker.sock:/var/run/docker.sock
|
|
networks:
|
|
- internal
|
|
depends_on:
|
|
- nginx
|
|
|
|
# ── Certbot (Let's Encrypt) ────────────────────────────────────────────────
|
|
certbot:
|
|
image: certbot/certbot:latest
|
|
container_name: certbot
|
|
restart: unless-stopped
|
|
volumes:
|
|
- ./certs:/etc/letsencrypt
|
|
- certbot_webroot:/var/www/certbot
|
|
entrypoint: >
|
|
/bin/sh -c "
|
|
trap exit TERM;
|
|
while :; do
|
|
certbot renew --webroot -w /var/www/certbot --quiet;
|
|
sleep 12h &
|
|
wait $${!};
|
|
done
|
|
"
|
|
|
|
volumes:
|
|
forgejo_data:
|
|
geoip_db:
|
|
certbot_webroot:
|
|
nginx_logs:
|
|
|
|
networks:
|
|
internal:
|
|
driver: bridge
|