CONTEXT: R-356 design decision (v0.219.0)
gates / gates (push) Successful in 11s

This commit is contained in:
2026-08-22 13:26:57 +02:00
parent c1dbb05ad6
commit 0f3cf0dbb2
+39 -1
View File
@@ -7,7 +7,45 @@
>
> Ask Claude Code: "Please update CONTEXT.md with what we did today"
Last updated: 2026-08-22 (v0.218.0 — R-354/R-355: the abandoned database, and the volumes the off-site restore never returned)
Last updated: 2026-08-22 (v0.219.0 — R-356: the off-site restore refused every app that has no data drive)
> **2026-08-22 — v0.219.0 (R-356). One predicate was answering two questions.**
>
> **[DESIGN] The restore destination is resolved by the SAME rule as the capture destination.** The
> drive if the app declares one, the system data path otherwise — `Manager.GetAppDrivePath`, one
> expression, now used by `CaptureRecoveryUnit`, `ReconstituteFromOffsite` and `PlaceOffsiteRestore`
> alike. Anything else and the restore aims somewhere the backup never came from, which surfaces as a
> placement-mismatch prompt on a box where nothing actually moved.
>
> **The refusal that protects a drive app from being restored onto the wrong disk (R-253, R-351)
> applies to apps that HAVE a drive to get wrong.** It used to be reached by `HDD_PATH == ""`, which
> also stood in for "is this app installed?". Measured in the catalogue at `459766cb1639`: **53
> templates, 13 `needs_hdd: true`, 40 `false`** — so for 40 apps that test was permanently true and the
> off-site restore refused them forever, while they were running, telling the customer to reinstall
> them "in the same place", which those apps never offer. **An app with no drive is not misconfigured**
> (`01-topology-and-trust.md` §8, `[DESIGN]`); it is the majority case, and between 19 and 22 August it
> was called a defect four times.
>
> **Now:** *installed?* is asked of `ListDeployedStacks()` via `Manager.isStackDeployed`, which **fails
> CLOSED on a nil provider** — "cannot tell" must not become "go ahead" when the next act is a write.
> *Where?* is asked of `GetAppDrivePath`. A third refusal, with its own sentence and its own route,
> covers installed-but-no-resolvable-data-root: widening `nincs telepítve` to cover that would send a
> customer to reinstall a running app and hide the real fault.
>
> **FENCED, and not changed:** `offboxCaptureSet`'s raw `GetStackHDDPath` (`offbox_capture.go:43`).
> Capture resolves an app's declared `userdata`/`import` file legs against that value; a system-data
> fallback there would write a snapshot claiming to hold the customer's files and not holding them. The
> fenced ACT is "introduce a fallback into capture-side path resolution" — reading the value elsewhere
> is fine.
>
> **Proven live on `demo-hp`, 2026-08-22.** `privatebin` (driveless): planted through the app's own
> HTTP API plus a direct file plant, off-sited, **deleted**, restored through
> `POST /backup/offbox/reconstitute` — **15/15 files back byte for byte**, two Hungarian accented names
> included, message „0 fájl és 1 adatkötet visszaállítva". The scratch was unit-only, exactly the shape
> nobody had ever driven to completion before, and every downstream leg held. `calibre-web` (drive
> app) walked the same way and did not move. Evidence:
> `felhom.eu/documentation/audits/DRILL-r356-hot-only-restore-2026-08-22/evidence/`.
> **2026-08-22 — v0.218.0 (R-354/R-355). The database nobody backed up, and the restore that
> returned most apps nothing.**