fix(BUG-018): append continue directive to UserPromptSubmit hook (cross-OS)#85
Merged
mlorentedev merged 2 commits intoMay 21, 2026
Merged
Conversation
…minators (cross-OS) User hit a SECOND blocker minutes after BUG-017 (PR #84) closed the EPIPE race -- and then a THIRD when the Stop hook also failed with the same "No stderr output" symptom in a 9-loop iteration. Original BUG-018 narrow scope (only UserPromptSubmit / session-init) was insufficient: ALL 5 claude-mem hooks that terminate with `node ... hook claude-code <event>"` lack the {"continue":true} directive that Claude Code requires after BUG-017's race fix removed the prior EPIPE-induced false-block: - SessionStart context -> `hook claude-code context` - UserPromptSubmit -> `hook claude-code session-init` - PostToolUse -> `hook claude-code observation` - PreToolUse -> `hook claude-code file-context` - Stop -> `hook claude-code summarize` The 6th hook (Setup, `node "$_P/scripts/version-check.js"`) is left untouched -- it fires only on plugin install/update, not the user hot path. Changes: 1. scripts/claude-mem-heal.sh::heal_hooks_json: sed substitution uses regex capture `\([a-z][a-z-]*\)` to match any `hook claude-code <X>"` terminator and append the directive in a single pass. 2. scripts/claude-mem-heal.ps1::Repair-HooksJson: PowerShell `-replace` with the equivalent regex; reports the count of hooks transformed. 3. tests/setup-linux.bats: 1 new parity assert covering the regex-based substitution + continue directive + BUG-018 reference in both heal scripts. Empirical (2026-05-21 user's Windows): - After BUG-017 merged: UserPromptSubmit failed (No stderr output) - After narrow BUG-018 manual patch: ping/pong worked, but Stop hook failed 9 times in a row (Claude Code's CLAUDE_CODE_STOP_HOOK_BLOCK_CAP forced override) - After regex-based patch (this commit) applied locally: all 5 hooks now end with the directive; subsequent prompts complete without loop. This PR persists the fix across `/plugin update` upstream reverts. Anti-scope: Setup hook (version-check.js) terminator left as-is. Future BUG-018b can extend if user encounters that hook in practice. Companion: - BUG-017 (PR #84 merged) -- EPIPE race prerequisite - upstream issue thedotmack/claude-mem#2607 -- root cause + 3 fix options for the cascade pipe; this PR's continue-directive append is independent layer addressing claude-mem#2188 (empty-stdin / hook protocol mismatch).
60454a2 to
4d82723
Compare
PR #85 had 69 LOC of production diff (heal scripts) which exceeds the 50-LOC spec-gate threshold. CI failed on spec-gate. Add proposal.md, tasks.md, verification.md describing the regex-based BUG-018 fix that patches all 5 `hook claude-code <X>` terminators. No code change; spec-only commit.
mlorentedev
added a commit
that referenced
this pull request
May 21, 2026
Move from specs/ to specs/archive/ per SDD lifecycle close (the folder move IS the archive marker; status: archived frontmatter update deferred to per-spec follow-up if needed). This session shipped (today, 2026-05-21): - AI-014-opencode-windows-bootstrap (PR #78) - BUG-014-claude-mem-marketplace-register (PR #75) - BUG-016-claude-mem-heal-v13-refresh (PR #83) - BUG-017-claude-mem-heal-hooks-json-race (PR #84) - BUG-018-userpromptsubmit-continue-directive (PR #85) - REFACTOR-003-diff-check-ps1 (PR #82) Catch-up archive (merged earlier weeks but specs/ folder lingered): - BUG-007-remove-github-plugin-broken (PR #65, 2026-05-19) - BUG-011-mcp-loop-claude-json-guard (PR #69, 2026-05-20) - BUG-012-claude-mem-marketplace-junction (PR #70, 2026-05-20) - SDD-005-github-copilot-instructions-sync (PR #62, 2026-05-19) - SDD-006-vault-integrity-check (PR #63, 2026-05-19) Active specs remaining in specs/ (not yet merged): - REFACTOR-002-paths-in-env-contract (queued, still draft) - WIN-002-windows-smoke-sweep (partial closure via PR #73, full clean-VM sweep still open) 33 file moves total (3 files per spec × 11 specs). Zero content change.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
User hit a SECOND blocker minutes after BUG-017 (PR #84) closed the EPIPE race:
```
UserPromptSubmit operation blocked by hook: ... No stderr output
```
The error MESSAGE changed (no more `printf: write error`), proving BUG-017 landed, but the hook still blocks. Root cause: claude-mem's UserPromptSubmit hook command terminates with `node ... hook claude-code session-init` and does NOT emit Claude Code's `{"continue":true,"suppressOutput":true}` directive.
When `bun-runner.js` receives empty stdin (upstream claude-mem#2188), it prints diagnostic to stdout. Claude Code reads this as non-JSON-directive output → blocks the prompt.
Other claude-mem hooks (SessionStart `start`) already emit the directive: `node ...; echo '{"continue":true,"suppressOutput":true}'`. UserPromptSubmit just didn't get the same treatment upstream.
Empirical validation (this branch, user's Windows)
Manually patched user's local hooks.json with the same logic before this PR shipped → user's new Claude Code session in hive proceeded normally (no UserPromptSubmit block). This PR persists the fix across `/plugin update` upstream reverts via the heal scripts.
Changes
42 LOC total. Production diff 26 LOC (below spec-gate threshold). Skip SDD per "mechanical mirror" rule.
Test plan
Anti-scope
Only UserPromptSubmit is patched here. The OTHER 4 hooks without the directive (Setup, SessionStart-context, PostToolUse, PreToolUse, Stop) stay untouched — only fix what user empirically hit. A future BUG-018b extends if those surface.
Companion PRs