fix(ops-agent): foundation-stap overslaan op een host die het doeladres niet bezit #137

Merged
janpeter merged 1 commit from fix/foundation-skip-on-foreign-host into main 2026-08-02 17:28:35 +02:00
Owner

setup.sh strandde op scrum4me-server op CONTROL_ROOM_FOUNDATION_FAILED: existing_foundation_state_ambiguous. Dat is geen toeval maar een portabiliteitsbug.

De bevinding

control-room-foundation.sh is aan één host gebonden — vier hardgecodeerde adressen, geen override, geen detectie:

regel constante waarde scrum4me-server
58 AGENT_ADDRESS 172.18.0.1:3099 klopt
59 LEGACY_ADDRESS 127.0.0.1:3099 listener is 172.18.0.1
60 TAILNET_ADDRESS 100.102.8.64:3099 100.118.195.120
61 FORBIDDEN_LAN_ADDRESS 192.168.0.158:3099 192.168.0.154

Plus TAILSCALE_IP (regel 322) en ops-agent-tailnet-proxy.socket met ListenStream=100.102.8.64:3099.

De staat-detectie valt door zowel de fresh- als de legacy-tak — met de listener op 0.0.0.0:3099 én daarna op 172.18.0.1:3099, het adres dat ops-agent.service:22 zelf voorschrijft. Er bestaat op deze host geen configuratie waarin de unit en dit script het eens zijn.

Alleen LEGACY_ADDRESS bijstellen was verleidelijk maar fout: require_listener_set en verify_listener (regel 290/292) eisen daarna een listener op TAILNET_ADDRESS. Dat verplaatst de fout naar een punt waar er al units geïnstalleerd zijn.

De oplossing

Een expliciete niet-van-toepassing-conditie, geen error-vangnet: bezit de host het doeladres niet, dan wordt de stap overgeslagen. Op de host waar het subsysteem wél hoort draait het onveranderd, en mag een echte fout de deploy gewoon laten falen.

Het doeladres wordt uit het script zelf gelezen, zodat er geen vijfde kopie ontstaat en de conditie meebeweegt als het subsysteem ooit host-onafhankelijk wordt.

SKIPPED: Control Room foundation NIET toegepast op scrum4me-server.
SKIPPED:   reden       deze host bezit 100.102.8.64 niet
SKIPPED:   gebonden aan de host met dat tailnet-adres
SKIPPED:   zie         deploy/ops-agent/scripts/control-room-foundation.sh:58-61
SKIPPED: de ops-agent is hierdoor NIET achter de tailnet-proxy gezet.

Bewijs

setup.sh              exit 0, tot ==> Done
config                101 keys, 18 flows
listener              172.18.0.1:3099
agent                 active, HTTP 200
whitelist-exec        preflight-migrations: OK (0 pending, 22 skipped), exit 0
drift (config+build)  no drift, exit 0
timer                 active / enabled
tailnet-proxy         inactive / not-found  (correct: overgeslagen)

De bevinding staat ook in docs/runbooks/control-room-foundation.md — overslaan lost het hier op en verbergt het op elke andere host.

`setup.sh` strandde op scrum4me-server op `CONTROL_ROOM_FOUNDATION_FAILED: existing_foundation_state_ambiguous`. Dat is geen toeval maar een portabiliteitsbug. ## De bevinding `control-room-foundation.sh` is aan één host gebonden — vier hardgecodeerde adressen, geen override, geen detectie: | regel | constante | waarde | scrum4me-server | |---|---|---|---| | 58 | `AGENT_ADDRESS` | `172.18.0.1:3099` | klopt | | 59 | `LEGACY_ADDRESS` | `127.0.0.1:3099` | listener is `172.18.0.1` | | 60 | `TAILNET_ADDRESS` | `100.102.8.64:3099` | **`100.118.195.120`** | | 61 | `FORBIDDEN_LAN_ADDRESS` | `192.168.0.158:3099` | **`192.168.0.154`** | Plus `TAILSCALE_IP` (regel 322) en `ops-agent-tailnet-proxy.socket` met `ListenStream=100.102.8.64:3099`. De staat-detectie valt door zowel de `fresh`- als de `legacy`-tak — met de listener op `0.0.0.0:3099` én daarna op `172.18.0.1:3099`, het adres dat `ops-agent.service:22` zelf voorschrijft. **Er bestaat op deze host geen configuratie waarin de unit en dit script het eens zijn.** Alleen `LEGACY_ADDRESS` bijstellen was verleidelijk maar fout: `require_listener_set` en `verify_listener` (regel 290/292) eisen daarna een listener op `TAILNET_ADDRESS`. Dat verplaatst de fout naar een punt waar er al units geïnstalleerd zijn. ## De oplossing Een **expliciete niet-van-toepassing-conditie**, geen error-vangnet: bezit de host het doeladres niet, dan wordt de stap overgeslagen. Op de host waar het subsysteem wél hoort draait het onveranderd, en mag een echte fout de deploy gewoon laten falen. Het doeladres wordt uit het script zelf gelezen, zodat er geen vijfde kopie ontstaat en de conditie meebeweegt als het subsysteem ooit host-onafhankelijk wordt. ``` SKIPPED: Control Room foundation NIET toegepast op scrum4me-server. SKIPPED: reden deze host bezit 100.102.8.64 niet SKIPPED: gebonden aan de host met dat tailnet-adres SKIPPED: zie deploy/ops-agent/scripts/control-room-foundation.sh:58-61 SKIPPED: de ops-agent is hierdoor NIET achter de tailnet-proxy gezet. ``` ## Bewijs ``` setup.sh exit 0, tot ==> Done config 101 keys, 18 flows listener 172.18.0.1:3099 agent active, HTTP 200 whitelist-exec preflight-migrations: OK (0 pending, 22 skipped), exit 0 drift (config+build) no drift, exit 0 timer active / enabled tailnet-proxy inactive / not-found (correct: overgeslagen) ``` De bevinding staat ook in `docs/runbooks/control-room-foundation.md` — overslaan lost het hier op en verbergt het op elke andere host.
fix(ops-agent): foundation-stap overslaan op een host die het doeladres niet bezit
All checks were successful
CI / Root app checks (pull_request) Successful in 5m44s
CI / Ops-agent checks (pull_request) Successful in 16s
CI / Deploy artifact checks (pull_request) Successful in 31s
CI / Docker image build (pull_request) Successful in 1m22s
4d54246dea
setup.sh strandde op deze host op CONTROL_ROOM_FOUNDATION_FAILED:
existing_foundation_state_ambiguous, en dat is geen toeval maar een
portabiliteitsbug: control-room-foundation.sh bevat vier hardgecodeerde adressen
(regel 58-61) plus een socket-unit met ListenStream=100.102.8.64:3099. Op
scrum4me-server klopt alleen AGENT_ADDRESS; het tailnet-adres daar is
100.118.195.120 en het LAN-adres 192.168.0.154.

Alleen LEGACY_ADDRESS bijstellen was verleidelijk maar fout: require_listener_set en
verify_listener (regel 290/292) eisen daarna een listener op TAILNET_ADDRESS, een
adres dat de host niet bezit. Dat verplaatst de fout naar een plek waar er al units
geinstalleerd zijn.

Daarom een expliciete niet-van-toepassing-conditie: bezit de host het doeladres niet,
dan wordt de stap overgeslagen met een luide SKIPPED-melding met hostnaam en reden.
Nadrukkelijk GEEN vangnet om fouten op te slokken — op de host waar het subsysteem
wel hoort draait het onveranderd en mag een echte fout de deploy laten falen.

Het doeladres wordt uit het script zelf gelezen, zodat hier geen vijfde kopie van dat
adres ontstaat en de conditie meebeweegt als het subsysteem ooit host-onafhankelijk
wordt gemaakt.

De bevinding zelf staat in docs/runbooks/control-room-foundation.md: overslaan lost
het op deze host op en verbergt het op elke andere.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Sign in to join this conversation.
No reviewers
No labels
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set.

Reference
janpeter/Ops-dashboard!137
No description provided.