# ═══════════════════════════════════════════════════════════════════════════════ # Evolu Relay - je eigen sync-server voor apps die op Evolu gebouwd zijn. # # Drie containers: de relay, een agent voor de statuspagina, en nginx die die # pagina serveert. Geen Postgres en geen quota-manager meer; die hoorden bij de # relay van Trezor, en die is als zelf-gehoste relay in de kern onbruikbaar omdat # de cliënt bij een eigen relay-URL nooit een eigenaar registreert. Zie het plan # Umbrelapp, OPEN.md punt 6, en de proef in PLAN.md §6a. # # De poortindeling is omgedraaid ten opzichte van 25-08-2026, en dat is de kern # van dit bestand: # # - de PAGINA hangt achter app_proxy, mét de inlog van umbrelOS. Vroeger stond de # relay daar en moest de inlog dus uit, waardoor een statuspagina net zo # onbeschermd zou zijn als de relay zelf; # - de RELAY publiceert zijn eigen poort, waar Zoraxy met TLS naartoe wijst. # een sync-cliënt is geen browser met een sessiecookie en zou achter de inlog # een inlogpagina krijgen in plaats van de relay. # # Dat is hetzelfde patroon als Electrum Gate in deze store: de web-UI via de # proxy, het protocol op een eigen poort. Zie PLAN.md §4h. # ═══════════════════════════════════════════════════════════════════════════════ services: # umbrelOS genereert deze service zelf; wij vullen alleen in waar hij heen moet # wijzen. De hostnaam heeft de vorm __1. # # PROXY_AUTH_ADD staat hier bewust NIET op "false". Dat stond er tot 0.0.2 wel, # toen de relay hierachter hing. Nu wijst dit naar de statuspagina, en die hoort # juist achter de inlog. Zet het niet terug zonder §4h te lezen. app_proxy: environment: APP_HOST: whatsnext-evolu-relay_server_1 APP_PORT: 80 relay: # Gebouwd uit tools/evolu-relay/ door build.sh en geduwd naar het # Gitea-register op dezelfde server als deze store. Dat moet: umbreld haalt # élke image op via de Docker Engine API en niet via compose, dus een lokaal # gebouwde tag is voor hem onbereikbaar en de installatie faalt met # "pull access denied". Op 25-08-2026 op het apparaat vastgesteld. # # De digest hoort erbij en niet alleen de tag: een tag kan opnieuw geduwd # worden en dan draait er iets anders dan hier staat. Staan ze allebei, dan # bepaalt de digest wat er gehaald wordt en is de tag alleen leesbaarheid. # Houd de tag gelijk aan `version` in het manifest en aan VERSION in build.sh. # # Let op: dit is één architectuur (amd64), want er is alleen amd64 gebouwd. # Voor de officiele store hoort er een multi-arch index-digest met arm64 in; # zie het masterplan Publicatie-Relay. # # ── LET OP: hier staat GEEN digest, en dat is tijdelijk ─────────────────── # 0.5.0 bestaat nog niet in het register: er zit een wijziging in de relay # (het tijdvenster voor nieuwe eigenaars) en die moet eerst gebouwd en geduwd # worden met `sh tools/evolu-relay/build.sh`. # # De digest van 0.3.0 stond hier en is weggehaald in plaats van blijven staan. # Dat is met opzet de minst erge van twee kwaden: staat er een tag én een # digest, dan bepaalt de DIGEST wat er gehaald wordt. Een oude digest onder # een nieuwe tag levert dus stilzwijgend de oude relay, en dan werkt de timer # niet zonder dat iets dat meldt. Ongepind faalt hard en zichtbaar zolang de # image er niet is, en dat is hier het gedrag dat je wil. # # Zet de digest uit de push-uitvoer er weer achter zodra 0.5.0 geduwd is; # tests/test_appstore_vorm.py drukt de pinstatus af, dus de suite blijft het # zeggen tot het gedaan is. image: sc.kamenier-hamer.nl/sysop/evolu-relay:0.5.0 restart: on-failure ports: # De relay zelf. Dit is de poort waar Zoraxy met TLS naartoe wijst, en de # enige die deze app publiceert; de pagina loopt via app_proxy. # # 3852 op de host en niet 4000: dat laatste is een veelgebruikte poort en # een botsing merk je pas als de app niet start. Dezelfde les als bij # Electrum Gate, dat om die reden 50022 gebruikt in plaats van 50002. # Binnen de container blijft het 4000, want dat is wat de relay verwacht. - "3852:4000" environment: RELAY_PORT: "4000" # Per schrijfactie en niet per eigenaar; zo is isOwnerWithinQuota bij Evolu # bedoeld. Eén labelwijziging is klein, dus een schrijfactie hierboven is # eerder een fout of misbruik dan normaal gebruik. Zie PLAN.md §4g. RELAY_MAX_WRITE_BYTES: "1048576" volumes: # De database van de relay én onze allowlist ernaast, in dezelfde map. Het # programma doet chdir naar `data`, net als de relay van Evolu zelf, dus dit # pad ligt vast. # # Onder data/ en niet in een naamloos Docker-volume: dit is wat umbrelOS # bewaart en meeneemt in de back-up. In een volume zou de synchronisatie een # herinstallatie van de app niet overleven. - ${APP_DATA_DIR}/data/relay:/app/data # De agent bedient de statuspagina. Hij beslist niets: hij leest wat het # relay-proces heeft opgeschreven en legt opdrachten in een postbus die de relay # zelf leegmaakt. Twee processen die in dezelfde allowlist schrijven is een # wedloop die je een keer per jaar treft en dan niet kunt reproduceren. agent: # TODO pinnen op de multi-arch index-digest, met # `docker buildx imagetools inspect python:3-alpine`. Geldt ook voor nginx # hieronder; staat als taak in het plan Umbrelapp. image: python:3-alpine restart: on-failure environment: RELAY_STATE_DIR: /var/lib/relay # De volledige containernaam en niet de servicenaam 'relay'. Bij Electrum # Gate gaf de korte naam op het apparaat een geweigerde verbinding: de naam # loste wél op, maar naar een container van een andere app op hetzelfde # netwerk. De vorm __1 is uniek per app. RELAY_HOST: whatsnext-evolu-relay_relay_1 RELAY_PORT: "4000" # Alleen om op de pagina het adres te tonen dat je in je cliënt invult. # Moet gelijk zijn aan de hostpoort hierboven. RELAY_PUBLIC_PORT: "3852" RELAY_API_PORT: "8000" PYTHONUNBUFFERED: "1" volumes: # Door umbrelOS ingevuld uit agent.py.template bij het starten. Er staat # geen accolade-variabele in dat bestand, dus de invulling laat de # Python-code ongemoeid; de agent leest zijn instellingen uit de omgeving # hierboven. De test in tests/ controleert die aanname. - ${APP_DATA_DIR}/agent.py:/app/agent.py:ro # Dezelfde map als de relay. De agent moet hier kunnen schrijven, want de # opdrachten van de pagina landen hier. - ${APP_DATA_DIR}/data/relay:/var/lib/relay command: - python - /app/agent.py server: image: nginx:alpine restart: on-failure # De agent moet er zijn voordat nginx start: de proxy_pass naar # http://agent:8000 wordt bij het starten opgelost en een onbekende naam laat # nginx afbreken. depends_on: - agent volumes: # Beide door umbrelOS ingevuld uit een .template bij het starten. - ${APP_DATA_DIR}/nginx.conf:/etc/nginx/nginx.conf:ro - ${APP_DATA_DIR}/index.html:/usr/share/nginx/html/index.html:ro # Het app-icoon, voor de kop van de pagina en het tabblad. Geen template, # dus dit bestand komt alleen bij een installatie mee en niet bij een # update; voor een plaatje dat vrijwel nooit wijzigt is dat goed genoeg. - ${APP_DATA_DIR}/icon.png:/usr/share/nginx/html/icon.png:ro