openai / openai/codex-plugin-cc
stop-review-gate-hook.mjs: fail-closed reason strings do not mention the /codex:setup --disable-review-gate escape valve
Nobody has claimed this yet.
- Dominant language
- JavaScript
- Stars
- 33.3k
- Forks
- 2.3k
- PR merge metrics
- No merged PRs in 30d
Description
Summary
When stopReviewGate: true, scripts/stop-review-gate-hook.mjs emits {"decision":"block","reason":"..."} on any of 5 fail-closed branches (timeout, task failure, invalid JSON, empty rawOutput, unexpected first-line). The reason string is the ONLY message operators see — Claude Code's Stop-hook does not offer a UI for hook decisions beyond the reason text.
The reason strings currently include "Run /codex:review --wait manually or bypass the gate." — but the concrete "bypass the gate" command is not spelled out. Operators in a fail-closed loop (e.g., 3 consecutive infra failures with empty rawOutput) cannot discover the escape valve /codex:setup --disable-review-gate from the message they see.
Failure scenario (observed)
A derivative Claude Code session on 2026-07-09 hit 3 consecutive status: 1 / rawOutput: "" failures from the underlying Codex CLI. Each time, the Stop hook fired at 15-min timeout limits and re-blocked. The session became terminaion-incapable — CC's built-in ~9-iteration recursive-stop limit was the only path out.
The operator recovered manually by finding the escape valve in tritool-side docs (.claude/rules/safety-gate.md §14). Without those tritool-side docs, the escape valve is not discoverable.
Proposed fix (3 options, any one closes the loop)
(a) Reason-string literal command (smallest change)
Append the literal command to all 5 fail-closed branches:
"Run /codex:review --wait manually or bypass the gate by running /codex:setup --disable-review-gate."
(b) Distinguish infra failure vs rule violation via reasonCategory field
CC's Stop-hook decision schema accepts extra fields. Adding:
{
"decision": "block",
"reason": "...",
"reasonCategory": "infra_failure" | "rule_violation"
}
lets downstream (e.g., tritool-side wrapper Stop hook) handle infra failures differently — e.g., downgrade to advisory after N consecutive infra failures.
(c) Consecutive-N counter + downgrade
Persist a counter in the plugin's state file (stateModule.setConfig). After N consecutive infra failures (recommended default N=3), downgrade decision: block → advisory ({"continue":true, "systemMessage":"..."}) so the session can terminate. Reset the counter on any allow / successful review / rule-violation block.
Reproduction
stopReviewGate: true(/codex:setup --enable-review-gate)- Make the underlying Codex CLI fail 3 times consecutively (e.g., simulate by unavailable auth or config drift)
- Observe Stop hook blocks each iteration with the same reason string
- Confirm the operator cannot discover the escape valve from the reason string alone
Environment
- codex-plugin-cc: v1.0.4 (sha
807e03aat time of investigation) - Claude Code: v2.1.198
- OS: Linux (verified 2026-07-09), likely applies to all platforms
Cross-reference
Tritool-template documented the discovery gap in docs/runbook-cc-codex-outage.md §8 (see linked repo URL) and .claude/rules/safety-gate.md §14 (Plugin hooks Stop row) as short-term workaround for their derivative projects. Filing here so the fix can land upstream and eliminate the need for the downstream doc.
Contributor guide
No contributing guide indexed for this repository
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
Research direction
Start with scripts/stop-review-gate-hook.mjs and inspect the five fail-closed branches that emit the block reason. Compare their current messages with the proposed escape-valve wording and decide which of the three proposed fixes is intended. Done means the selected fix covers the reported repeated-failure scenario and the operator can discover an escape path.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- javascript
- Domain
- tooling
- Issue type
- Bug
- Difficulty
- 3/5
- Estimated time
- 1-2 days
- Activity status
- Quiet
- Clarity
- Mostly clear
- Newbie friendliness
- 55/100