--- paths: ["internal/localapi/**", "internal/authz/**", "internal/guesthook/**"] --- # Local API, authz and guest hooks — the per-guest blast radius `internal/localapi/` is the narrow per-guest local API: token store, disks/format, guest binds, controller swap, stale-lock recovery, pinned self-signed leaf. `internal/authz/` is the operator signed-op verifier (SSHSIG) plus the durable nonce store. `internal/guesthook/` installs the pre-start self-heal hookscript. > **Overlap note:** `health-checks.md` also matches `internal/localapi/**` and > `internal/guesthook/**`. That is deliberate — both rules apply there and both load. Neither > supersedes the other. ## Scoping is the whole security property This API is reachable **from inside a customer guest**. Every route must be scoped to the guest that called it — a route that can name another guest's id has escaped its blast radius. Fail **safe to protected**: an unrecognised or unresolvable caller gets less access, never more. ## Replay protection must survive a restart **`authz.MemoryNonceStore` on a real host is a defect** — replay protection dies on restart. Use `authz.FileNonceStore`. The memory store exists for tests. ## The token is a hash on disk, plaintext only at mint The store keeps **hashes**. The plaintext token exists in exactly one place, `bootstrap.json` on the PVE host — so a "read the token" step means reading that file, and a lost token is re-minted, never recovered. ## Binds can brick guest boot | Do not | Because | Use | |---|---|---| | `GuestBinder.AttachBind`/`DetachBind` (per-drive `pct set -mpN`) | legacy model; a missing bind source can **brick guest boot** (C1) | `AttachDrive`/`DetachDrive` (intermediary model) | | `isHostMountpoint` to reconcile bind state | a boolean cannot converge stacked double-binds (the `/mnt` doubling bug) | `countHostMounts` normalization inside `AttachDrive` |