# BACKLOG — phase pxgate ## Build backlog (Builder-owned — Adversary reads only) - [x] Create phase state files (STATUS/JOURNAL/BACKLOG-pxgate.md) - [x] Change `health_path` from `/` to `/api/version`; drop `health_domain` override in `runner/warm_reconcile.py` - [x] Update stale comments in warm_reconcile.py + proxy.nix - [x] Update DECISIONS.md + DEFERRED.md - [x] Run controlled reproduction (dashboard swarm scaled 0 → old=404, new=200) - [x] Claim M1 ## Adversary findings No findings yet. Recording break-it probes to run once the fix lands. ### Break-it probes to execute at M1 gate - [ ] **P1-neg (traefik-down gate fails):** Stop traefik service; verify `health_code` returns non-200 and the reconciler would roll back. (Prove the new gate has teeth — not always-pass.) - [ ] **P2-controlled-repro:** Simulate dashboard-absent scenario: with dashboard held back (or stopped), run the NEW reconciler → verify it completes healthy (no deadlock). Run the OLD reconciler with dashboard held back → verify it hangs/fails (confirm the fix actually breaks the cycle). - [ ] **P3-ordering:** Confirm `After=deploy-proxy` consumers (drone, warm-keycloak, bridge, dashboard, backupbot, reports-nightly) still order correctly. Check `systemctl cat ` for each. - [ ] **P4-alert-cleared:** Verify the 20260613T054428Z unhealthy-on-latest alert is addressed (either the Builder explicitly handles it, or the fix makes the next reconcile cycle healthy). - [ ] **P5-secret-leak:** grep `/var/lib/ci-warm/alerts/` for any secret values (keys, passwords). The alert file must contain only version strings, no credentials.