Skip to content

An escalation lands in blocked, and does not read as a failed run - #176

Merged
thedancingdeveloper merged 1 commit into
mainfrom
fix/escalation-is-not-a-failure
Aug 5, 2026
Merged

An escalation lands in blocked, and does not read as a failed run#176
thedancingdeveloper merged 1 commit into
mainfrom
fix/escalation-is-not-a-failure

Conversation

@thedancingdeveloper

Copy link
Copy Markdown
Contributor

Two defects in #175, both found by running rdpapp R7 against it.

Stop(state=BLOCKED) never reached the queue. Only the checks path copied stop.state across; every other path left the item failed. R7 was recorded escalated / item_impossible, attempts=0 — all correct — and sat in failed, invisible to the person it was raised for. Now applied centrally at the release call.

The run said FAIL R7 and set exit 1. Nothing went wrong and no attempt was spent. There is now a YOU marker, a waiting on you, not on a retry line, and escalations are excluded from the exit status — otherwise a queue of well-formed questions reads to CI as a broken run.

run_summary() is extracted and returns lines, so the decision can be tested rather than living inside a print loop.

Four new tests; all four gates green locally.

🤖 Generated with Claude Code

Both found by running rdpapp R7 through the path added in #175. The agent
refused an impossible item correctly, with citations, and the harness then
mishandled the answer twice.

**The state never reached the queue.** `Stop(state=BLOCKED)` was honoured only
on the checks path, which copied `stop.state` across by hand; every other path
left the item in `failed`. So R7 was recorded `escalated / item_impossible`
with `attempts=0` — all correct — and sat in `failed`, where nothing looking
for work that needs a person would ever find it. The state is now applied
centrally, at the release call, beside `consumes_attempt` which was already
read there. An empty `state` still means the caller chose, which is every path
older than this taxonomy.

**The run announced it as `FAIL R7`.** `ok` and `FAIL` were the whole
vocabulary, so an outcome where nothing went wrong and no attempt was spent was
reported as a failure — and set exit 1, which makes a queue of well-formed
questions read to CI as a broken run. There is now a `YOU` marker, a closing
`waiting on you, not on a retry` line, and `_is_failure` excludes
`NEEDS_A_PERSON` from the exit status.

The summary is extracted as `run_summary()` returning lines rather than
printing them, because a formatting decision that only exists inside a print
loop cannot be tested, and this one is a decision.

One older test asserted `FAILED` for a clean tree while its own docstring said
"that is a real answer, not a failure to paper over". It asserts `BLOCKED` now.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
@thedancingdeveloper
thedancingdeveloper merged commit df54a28 into main Aug 5, 2026
2 checks passed
@thedancingdeveloper
thedancingdeveloper deleted the fix/escalation-is-not-a-failure branch August 5, 2026 03:24
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant