Development record
Host-payload refusals outside ideate still quote the refused value into the error text. Found on the sweep for iss-2609090951295881, which fixed the six ideate sites: lifeboat synthesis_review.go quotes an out-of-set mode, prompt_version and verdict with a bare %q (no redaction, no sanitising beyond Go quoting); intent audit.go quotes an out-of-enum criterion verdict, a malformed criterion id, a _type and a receipt id the same way (its dead-letter RECORD is redacted, the returned error is not). Each field arrives in a host-composed payload beside free text the verb does redact, so a token or home path pasted into a closed-set field is printed verbatim to the terminal and transcript on refusal. The reading ingest routes its quoted values through echo(); whether that redacts or only bounds is unverified. Fix direction: the ideate describeRefused shape (length, never the value), shared rather than copied. Detector: for each payload verb, a closed-set field carrying a sentinel must be refused without the sentinel in the error.
Host-payload refusals outside ideate still quote the refused value into the error text. Found on the sweep for iss-2609090951295881, which fixed the six ideate sites: lifeboat synthesis_review.go quotes an out-of-set mode, prompt_version and verdict with a bare %q (no redaction, no sanitising beyond Go quoting); intent audit.go quotes an out-of-enum criterion verdict, a malformed criterion id, a _type and a receipt id the same way (its dead-letter RECORD is redacted, the returned error is not). Each field arrives in a host-composed payload beside free text the verb does redact, so a token or home path pasted into a closed-set field is printed verbatim to the terminal and transcript on refusal. The reading ingest routes its quoted values through echo(); whether that redacts or only bounds is unverified. Fix direction: the ideate describeRefused shape (length, never the value), shared rather than copied. Detector: for each payload verb, a closed-set field carrying a sentinel must be refused without the sentinel in the error.
Grounds
- pursued: neither verb returns a refused payload value unredacted; a sentinel in the lifeboat review's closed-set fields, or a planted path in an audit verdict token, that reaches the returned error or reason would show it wrong
Frontmatter
| id | iss-2609290033521472 |
|---|---|
| type | issue |
| lifecycle | resolved |
| severity | minor |
.abcd/work/issues/resolved/iss-2609290033521472-host-payload-refusals-outside-ideate.md
open on GitHub ↗ · commit history ↗
mentions3
- iss-2609090951295881The ideate verdict recorder states its redaction discipline in the stage-two refusal type: a refusal that quoted the span it refused would publish the leak into the error message, and from there into a terminal and a log, so that error names the finding kinds and nothing else. The enum refusals in the same file do the opposite. Five sites, the verdict, the leg kind, the claim status, the grill relation and the kill outcome, interpolate the offending value into the message after passing it only through the terminal-escape cleaner, which strips control sequences and does not redact. Every one of those fields arrives in the host payload alongside the free-text fields the recorder does redact field by field, so a payload whose status field carries a token or a home path is refused with nothing written and that value printed verbatim to the error surface, where the session transcript and any capture outside abcd take it raw. Verified by reading the five call sites. It matters because the file argues at length that a fail-closed promise is only honest if the refusal itself carries nothing, and these five refusals are the exception nobody wrote down. Fix direction: describe the offending value rather than quoting it, since its length and whether it is empty is enough to fix a typo, or route it through the same field redactor the prose fields already use before it reaches the message. Detector: an ideate payload whose enum field carries a token-shaped value must be refused without that value appearing anywhere in the error text.
- iss-2609290043245353The reading ingest's refusals echo payload-chosen values unredacted. echo() in internal/core/reading/ingest.go cleans a value (termsafe.CleanProseLine) and caps it at maxEchoedBytes (120), but runs no privacy redaction, and 17 call sites use it: the output's _type, run_id, manifest_sha256 and position among them, beside values the manifest (abcd-written) supplies. A reading output whose closed-set or id field carries a token or a home path is refused with up to 120 bytes of it in the error, which reaches the terminal and the transcript. Found on the sweep for iss-2609290033521472, which fixed the same shape in lifeboat review and intent audit with termsafe.DescribeRefused and the audit redactor. Fix direction: per site, describe a payload value (DescribeRefused) or route it through the reading's own payloadField redactor (redact.go), leaving manifest-sourced values as they are. Detector: a reading output carrying a sentinel in each quoted field is refused without the sentinel in the error.
- iss-2609290144116254The intent consistency ingest's refusals echo payload-chosen values unredacted. validateConsistency in internal/core/intent/consistency.go quotes the findings payload's _type with a bare %q (line 804, the same shape iss-2609290033521472 fixed in the audit ingest), and quotes a hash value (873), a finding's class and severity (938, 941), an end's path (993) and quote (1000) through oneLine, which cleans and caps but runs no privacy redaction. Each refusal returns to the surface, so a token or home path pasted into one of those fields reaches the terminal and the transcript. Found on the sweep for the audit.go _type fix (fix2-drainSec). Fix direction: describe a closed-set value (termsafe.DescribeRefused) and route path and quote through the verdict-prose redactor, deciding per site whether the echoed value is needed to find the fault. Detector: a findings payload carrying a sentinel in each quoted field is refused without the sentinel in the error.