/channel/{kind}/{index}/headAmp (and /source/{id}/headAmp) for a channel with no preamp to
read right now — amendment 2026-09-17 (reac-head-amp-control.md §12, ruled: "We should make
these elements computed so that they are not enabled when they do not exist anymore.").
A REAL VALUE, deliberately, not undefined: a import('./resource.js').ConsoleResource
whose read() answers undefined has no instance and therefore no broadcast to send
(ResourceRegistry.reprojectOn's absence path carries no broadcast at all) — so a channel
that goes from patched to unpatched while a client is already watching never told it, which is
the bug this row exists to close. Turning "nothing here" into an ordinary PRESENT read with
present: false lets the existing broadcast-on-change machinery carry the transition, exactly
as it would carry any other field's change — no second "removed" event vocabulary.
/channel/{kind}/{index}/headAmp(and/source/{id}/headAmp) for a channel with no preamp to read right now — amendment 2026-09-17 (reac-head-amp-control.md§12, ruled: "We should make these elements computed so that they are not enabled when they do not exist anymore.").A REAL VALUE, deliberately, not
undefined: a import('./resource.js').ConsoleResource whoseread()answersundefinedhas no instance and therefore no broadcast to send (ResourceRegistry.reprojectOn's absence path carries nobroadcastat all) — so a channel that goes from patched to unpatched while a client is already watching never told it, which is the bug this row exists to close. Turning "nothing here" into an ordinary PRESENT read withpresent: falselets the existing broadcast-on-change machinery carry the transition, exactly as it would carry any other field's change — no second "removed" event vocabulary.