DUNIN7 · LOOMWORKS · RECORD
record.dunin7.com
Status Current
Path standing-notes/loomworks-standing-note-companion-must-not-claim-what-system-did-not-do-v0_4.md

Loomworks Standing Note — The Companion Must Not Claim What the System Did Not Do

Version. 0.4 Date. 2026-08-14 (v0.3: 2026-08-12; v0.2: 2026-08-12; v0.1: 2026-06-27) Supersedes. v0.3, whose content stands in full below; v0.4 adds the third revision (the truthful server message destroyed by the client that receives it) and the layer-inversion observation, at the Operator's direction. Status. Standing note for the Loomworks project. Surfaces whenever a Companion response asserts that an action happened, offers an action, or names a feature — i.e. whenever the Companion's words make a claim about system state or capability. Origin. Three failures found in Operator testing (2026-06-27), all the same shape: the Companion's words claimed something the system did not do or cannot do. Lineage. Same family as correctness-guarantees-in-code-not-prompts, FORAY-emission-belongs-at-the-auditable-event-layer, and database-as-definition-layer-not-decision-layer. All four say: the guarantee must live in the substrate, not depend on a surface (or a script) cooperating. This note applies that family to what the Companion says.


What the principle says

The Companion must only claim an action happened if the system actually performed it. It must only offer an action it can actually perform. It must only name a feature that actually exists.

The Companion's words are a surface. Right now, that surface can say things the substrate never did:

The defect is the same in all three: the Companion's reply is decoupled from what the engine actually did or can do. The response is emitted by a script (a prompt) that assumes success, independent of whether success occurred. The words follow the script, not the system.

The principle closes that gap: the Companion's success-claims, offers, and feature-references must be gated on real system state — emitted because the engine confirmed the action, set up the offer, or has the feature, not because a prompt told the responder to say so.

The three instances (the evidence)

| # | The Companion said | What the system actually did | The gap | |---|---|---|---| | A | "Done — I've stopped using that." (remove flow) | Nothing — the assertion was untouched, still committed, no retraction event written. The confirmation branch needs is_confirmation_turn AND len(matches)==1; the match didn't resolve to one, so retract_assertion never ran — but the responder emitted the scripted success line anyway. | A success claim with no action behind it. | | B | "Want me to save that?" (remember-about-me Stage 1) | The note was mis-classified as general_conversation; the responder free-formed an offer with no held-write set up behind it. | An offer with no action behind it. | | C | "If you want it permanently erased, that option will be available in your settings." (every retraction) | No such setting, no assertion-erase endpoint exists. The sentence is hardcoded in the prompt (forget_about_me.md:7); "in your settings" is the generic _LOCATION_FALLBACK filler. | A feature promise with no feature behind it — and a feature that, if built as worded, would violate corrections-preserved (permanent erasure destroys the record the seed keeps as a correction). |

A and B are success/offer decoupling. C is a feature-reference decoupling. All three are the same principle violated.

What honoring the principle looks like

Success claims gate on the action. "Done" is sayable only when the engine confirms the action ran. If the retraction didn't persist, the Companion must not say it did — it should say what actually happened (e.g. "I couldn't find a single matching note to remove — did you mean one of these?") rather than a scripted success line. The success language is emitted from the engine's confirmed result, not scripted into the prompt as an assumption.

Offers gate on capability. The Companion offers to save/remove/produce only when the path to actually do it is set up. An offer the system can't fulfill is the start of a loop (instance B became the remember-about-me stall).

Feature-references gate on existence. The Companion names a setting, a button, or a capability only if it exists. No prompt should script a promise of an unbuilt feature. (And no prompt should promise a feature the seed forbids — instance C's "permanent erasure" is both unbuilt and seed-violating.)

The structural form: wherever possible, success language should be driven by the engine's result, not authored in the responder prompt as a fixed string that assumes the result. A prompt that says "on a confirmed retraction, say 'Done'" is the trap — it fires the success line on the intent to retract, not the fact of retraction. The fact must gate the words.

Where the principle is not load-bearing

It does not require the Companion to be terse or robotic — natural, warm phrasing is fine, as long as the claim is true. It does not forbid the Companion from describing things it will do as part of a confirmed flow. It governs claims about completed actions, offers of actions, and references to features — the places where words assert system state. Conversational text that makes no such claim (explanation, discussion, acknowledgement) is unaffected.

Revision, 2026-08-12 — server-composed is necessary, not sufficient (the Operator's ruling, recorded at their direction)

Every remedy this note produced — CR-2026-199's structural fix, B-87's denial, CR-2026-201's four all-claim conversions — rested on one conclusion: take the microphone away and the claim becomes safe. Server composition was the destination.

The dead-doors scoping (2026-08-12, inspection-briefs/loomworks-dead-doors-scoping-v0_1) found the counterexample: a server-composed unarmed promise. Door 2's creation closer — "…say the word and I'll set it up" — is a fixed server string (_DOOR2_CLOSING_TURN), composed exactly where this note says claims should live. And it promises what the taxonomy cannot honor: the measured success set for "the word" is two menu phrases the Operator is never shown; every natural go-ahead routes to a dead-ending sibling intent, deterministically.

The revised conclusion: server-composed is necessary, not sufficient — the words must also be ARMED, and nothing in the composition layer checks that. Taking the microphone away guarantees the words are the ones the server chose; it guarantees nothing about whether the system behind those words exists, is wired, or is reachable by the reply the words invite. A server string promising an unwired action is instance C's feature-promise decoupling with better provenance — the same defect, now provably not cured by composition alone. The gate this note demands ("offers gate on capability") applies to server strings with full force: a composed offer must be composed against the wiring that fulfills it, the way composed success-claims are composed against the engine's confirmed result.

Second revision, 2026-08-12 — the persisted instruction that outlives its affordance (the Operator's ruling, recorded at their direction)

The E0128 walk (inspection-briefs/loomworks-e0128-walk-findings-v0_1) found a member the first revision doesn't cover: "Your project is ready — tap your passkey to make it official." was composed against real wiring — the ceremony existed, armed, on the surface that received the live response. But the sentence was persisted into the transcript while the affordance lived in ephemeral response state (request_action, never persisted; the ceremony component mounted nowhere the transcript re-renders). The Operator landed on the candidate's own page, read the instruction, and exhausted every control finding nothing that commits.

Not an unarmed promise — an armed one that survives its own arming. The instruction outlives the only surface that can honor it. The composition was truthful at the moment it was served and false at every moment it was re-read.

The rule this adds: a composed IMPERATIVE that will be persisted must not name an act whose affordance is ephemeral. Either the affordance is derivable wherever the sentence re-renders (state-carried, not response-carried), or the persisted sentence must describe STATE, not instruct action — "drafted, not yet committed" stays true forever; "tap your passkey now" is a promise that outlives its context. Composition-time truth is not persistence-time truth, and nothing in the composition layer checks the difference — the same blindness the first revision named, now on the time axis.

Third revision, 2026-08-14 — the truthful server message destroyed by the receiving client (the Operator's ruling, recorded at their direction)

The E0128 commit diagnosis ([B-95], completion record CR-2026-207 v0.3) found the member that inverts the note's premise: the server named the cause truthfully on all four attempts409 not_converged, "Seed has 1 open finding(s)", in the response body — and the surface discarded it and asserted a different cause: "Couldn't commit — try your passkey again." Not a model overclaiming; not a stale promise; a catch block collapsing every non-401 into one message.

The rule this adds: a client that collapses distinct server errors into one message does not lose information — it MANUFACTURES a false claim. "Something went wrong" is honest about ignorance; "your passkey failed" is a claim, and when the server said otherwise it is a false one. Error handling is a composition surface, and every gate this note imposes on composed success-claims applies to composed FAILURE-claims with equal force: a failure message must be composed against the server's stated cause, or confess ignorance.

The layer inversion, worth naming: the note's arc has now walked every layer. Server composition was necessary but not sufficient (first revision — the unarmed server promise); then a composed imperative outlived its affordance (second revision — truth on the time axis); and now a truthful server message is destroyed by the client that receives it. Every layer has now been the one that broke it. The guarantee cannot be assigned to a layer; it is a property of the whole path from engine fact to rendered words, and each revision found the path's next unguarded segment.

Status of the pattern

Three confirmed instances — strong enough to name now, not wait for a fourth. The immediate fixes (gate instance A's "Done" on the real retraction; remove instance C's invented promise; instance B is the remember-about-me loop, separately scoped) close the known cases. The systematic follow-on is to audit the responder's scripted success-claims, offers, and feature-references for other places a prompt assumes a result the engine hasn't confirmed — because three instances means there are likely more untripped.

If the systematic audit lands, this note is a candidate for promotion into the methodology document proper alongside the other substrate-trust principles.


DUNIN7 — Done In Seven LLC — Miami, Florida Loomworks Standing Note — The Companion Must Not Claim What the System Did Not Do — v0.4 — 2026-08-14 Three instances: a success claim, an offer, and a feature promise, each decoupled from system reality. The Companion's words must be gated on what the engine actually did, can do, and has. One confirmed pattern; immediate fixes + a systematic audit follow.