From 998aa319588f46e073a5adefc817d994f417e543 Mon Sep 17 00:00:00 2001 From: kisfenyo Date: Thu, 3 Sep 2026 12:02:30 +0200 Subject: [PATCH] =?UTF-8?q?REPORT:=20v0.234.0=20=E2=80=94=20the=20backfill?= =?UTF-8?q?=20proven=20live,=20and=20a=20test=20of=20mine=20that=20went=20?= =?UTF-8?q?red=20overnight?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Adds section 6b (the startup backfill on both demo boxes: all nine apps already had records by the time it was ready, so the pre-0.233.0 shape had to be recreated on demo-hp - said plainly rather than papered over; two seeded with digests matching independently-read ground truth, seven untouched, nine badged) and 6c (the render test hardcoded a date and an age, was green the day it was written and red the next morning, now derived; R-457 names six candidate files). Also records what was deliberately NOT staged live: the backfill's refusal of a partial observation needs a degraded app, and manufacturing one risks the false customer email class that already cost 61 mails. --- REPORT.md | 65 ++++++++++++++++++++++++++++++++++++++++++++++++++++--- 1 file changed, 62 insertions(+), 3 deletions(-) diff --git a/REPORT.md b/REPORT.md index a673ed8..f7982af 100644 --- a/REPORT.md +++ b/REPORT.md @@ -1,8 +1,17 @@ -# REPORT — v0.233.0, update arc slices 1 & 2 (2026-09-02) +# REPORT — v0.234.0, update arc slices 1, 1b & 2 (2026-09-03) *Overwritten each run. This records the most recent implementation only.* -> **Read this first: one claim in the task turned out to be wrong, and it is a path, not a fact.** +> **v0.234.0 (2026-09-03) — read this first.** v0.233.0 shipped with *"the record only appears after +> the next lifecycle action"* written down as an ACCEPTED LIMITATION. **The operator found it the next +> morning and it was a defect:** OpenGist on demo-felhom, up 15 hours, running exactly the catalog pin, +> showing **no badge at all**. On a quiet box "fills in gradually" means "never", and a feature that +> fills itself in on an event nobody triggers is, on the quiet installations, **not shipped**. +> `Manager.BackfillInstalledImages` now seeds the absences at startup by READING containers — it +> starts nothing, restarts nothing and writes no compose file. **Proven live on both demo boxes** +> (§6b). **A test of mine also went red overnight** and that is §6c. +> +> **Read this second: one claim in the task turned out to be wrong, and it is a path, not a fact.** > The task cites source as `internal/stacks/deploy.go`, `internal/web/funcmap.go` and so on. **The Go > module lives under `controller/`** — every one of those is `controller/internal/...`. **Every line > number in the task was EXACT against the baseline** (`AppConfig` 99, `runComposeDeploy` 395, @@ -41,16 +50,18 @@ tolerance WARN), `controller/internal/web/funcmap.go`, `controller/internal/web/ | repo | commit | what | |---|---|---| | felhom-controller | **`8025304acc0a6737`** | v0.233.0 — the record and the badge | +| felhom-controller | **`38d28b5b624c`** | **v0.234.0 — the startup backfill + the calendar-bomb fix** | | app-catalog-felhom.eu | `69761cf91bfc` | `catalog_since` on all 53 apps + the `CLAUDE.md` rule | | app-catalog-felhom.eu | `8220f8dc…` | the catalog's own REPORT | | felhom.eu | `6035dfcc3ae1` | `09-update-architecture.md`, the register, roadmap, capability map, STATUS, live evidence | | felhom.eu | `e86cf42e0ba5` | R-454..R-456, filed because the observations gate refused a report that filed none | +| felhom.eu | `bc47dd4ef997` | v0.234.0 docs: the living architecture doc's limitation 3 struck, R-457, capability map, STATUS | No branches. All three gate runs passed on push (controller: 13 gates OK + 1 advisory, see §9). ## 4. Tests, and both companion red-proofs -**1707 → 1724 test functions (+17). 28 packages, 0 FAIL**, `go build ./... && go vet ./... && go test ./...`. +**1707 → 1729 test functions (+22; +17 in v0.233.0, +5 in v0.234.0). 28 packages, 0 FAIL**, `go build ./... && go vet ./... && go test ./...`. | group | what it pins | |---|---| @@ -212,10 +223,58 @@ observable on the shipped artifact, and **not** a rendered page: healthy. **This run provisioned nothing** — no guest, no storage, no hub record — so there is no teardown to report on any of the three layers. +## 6b. v0.234.0 — the startup backfill, proven live on both boxes + +**The honest complication first:** by the time 0.234.0 was ready, **all nine deployed apps on demo-hp +and the one on demo-felhom already carried records** — the overnight backup cycle had restarted them +and v0.233.0's recorder fired on every one (`opengist` is stamped `2026-09-03T00:31:11Z`). **The +natural fleet state could no longer exercise the new code.** + +The pre-0.233.0 shape was therefore recreated on **demo-hp** (Tier 0): the `installed_images:` block +was deleted from `privatebin` (1 service) and `romm` (**3** services) — a record, never data — and the +controller restarted. Ground truth was read from the containers first. + +``` +09:59:45 installed-images backfill: privatebin recorded 1 service(s) (privatebin/pdo:2.0.5 (sha256:8a2cac16eff6…)) +09:59:45 installed-images backfill: romm recorded 3 service(s) (rommapp/romm:5.0.0 (sha256:91f6611eca5a…), + mariadb:11.4 (sha256:4f1d8d202fcf…), redis:7-alpine (sha256:ff02b58f971e…)) +09:59:45 installed-images backfill: 2 app(s) recorded, 7 already had a record, 0 left unrecorded +``` + +- **Exactly the two stripped apps were seeded; the other seven were untouched** — the never-overwrite + rule observed, not asserted. +- **Every digest matches the independently-read ground truth.** +- **`/stacks` then carried „Naprakész" ×9**, one per deployed app, negative control `zzz-never-present` + at **0**. +- On demo-felhom the operator's own case renders the badge on `/stacks?filter=running` and + `/apps/opengist`. +- Backups removed from the box; **nothing provisioned**, no app started, stopped or upgraded. + +**NOT staged live, and the choice is the point:** the refusal half — that a partial observation is not +seeded — needs a degraded app, and manufacturing one is a dead-app alarm candidate. **This project has +already paid for 61 false customer e-mails from that class (R-330)**, so it is covered by +`TestGroupG_BackfillRefusesAPartialObservation` **with a companion red-proof** (remove the guard → +*"backfilled 1, want 0"*) and recorded here as unproven-live. + +## 6c. A test of mine was a calendar bomb, and the suite caught it + +`TestGroupD_BadgeRendersOnBothSurfaces` hardcoded a fixture `catalog_since: "2026-07-18"` **and** the +expected string `"Frissítés elérhető — 46 napja"`. The pure badge tests inject a clock; **the render +test cannot** — it goes through the production templates, which call the funcmap entry, which reads +`time.Now()`. Green on 2026-09-02, **red on 2026-09-03** with *"the behind badge is missing"* on both +surfaces, because the true answer had become 47. + +Fixed by **deriving** the fixture: `catalog_since` is computed as *today minus 46 days*, so it asserts +the real number through the real clock and cannot rot. **FILED: R-457**, which also names six other +test files carrying both a date literal and `time.Now()` — as unchecked candidates, not accusations, +because mixing the two is only a defect where the literal feeds a clock-evaluated assertion. + ## 7. NOT yet live-validated — an explicit list **Everything the task asked to be validated live, was.** What remains: +0. **The backfill's REFUSAL of a partial observation** — §6b explains why it was not staged live. + 1. **The fourth badge state, „Frissítés elérhető" WITHOUT an age.** It needs an app whose `catalog_since` is absent, malformed or future-dated, and all 53 catalog apps now carry a valid one. Covered by `TestGroupF` (absent, blank, `tegnap`, `18/07/2026`, `2026-13-45`, future-dated).