Repository navigation
TUI: AskUserQuestion modal is undismissable on v1.14.50 (Esc/Ctrl-C/Ctrl-X all no-op, traps user in question loop) #28112
Description
Summary
AskUserQuestion (or equivalent question/modal tool) renders a question pane that is completely undismissable under the Claude Opus 4.7 orchestrator. Esc, Ctrl-C, and Ctrl-X all no-op. Arrow keys + Enter do navigate and submit a selection, but after submission a new identical question appears, trapping the user. Worse — characters typed while attempting to recover land in the "Type your own answer" field as silent state corruption that persists across re-renders.
This is not the ESC-race issue #20095 (fixed in v1.3.3+ via the Effect/Runner migration). I am on v1.14.50 — that code path is gone. This is a new failure mode.
Closest open/closed cousins: #9284 (auto-closed stale, model-side loop), #11367, #26849, #23515 (all open UX issues).
Environment
| Field | Value |
|---|---|
| OpenCode version | 1.14.50 |
| Model | Claude Opus 4.7 (github-copilot/claude-opus-4.7) via Copilot provider |
| Agent | built-in Orchestrator |
| OS | macOS 26.4.1 (Build 25E253) |
| Kernel | Darwin 25.4.0 arm64 (Apple Silicon, T6041) |
| Terminal | iTerm2 |
| Multiplexer | tmux 3.x on private socket (-L concierge) |
| MCPs connected | context7, delphi, grep_app, quicker, salesforce-dx, second-brain, tech-playbook, websearch |
Steps to reproduce
- Run an Orchestrator agent on Claude Opus 4.7 with a long-running multi-perspective workflow.
- The agent eventually emits a
AskUserQuestion-style modal with 6 options + "Type your own answer". - User presses
Esc— modal does not dismiss. - User presses
Ctrl-C— no effect. - User presses
Ctrl-X— no effect. - User attempts to type a free-text reply ("continue", with a typo
contineu) — characters land in the "Type your own answer" field but noEnteris fired (TUI swallows it because the input is in select-mode, not text-mode). - User then arrow-navigates (
Down Down) to option feat: model config persistence #3 and pressesEnter. - Option feat: model config persistence #3 IS submitted — agent proceeds, does real work (
git commit,git push, updates a status file). - Agent emits "Going to waiting" and is genuinely idle.
- BUT the original modal is still visible, with the
contineutypo still in the custom-answer field and option feat: model config persistence #3 still checkmarked from step 7. A second identical question is queued behind it. User is trapped in the loop again.
Expected
Escshould dismiss the modal cleanly and return to the normal prompt.Ctrl-Cshould interrupt the in-flight question and return control to the user.- After a successful selection +
Enterin step 7, the modal should fully tear down before the agent fires a new one.
Actual
Esc/Ctrl-C/Ctrl-Xare dead-keys while the modal is open.- Free-text typed while in select-mode silently corrupts the "Type your own answer" field — the user has no visual indication this is happening, and the corruption persists across modal re-renders.
- Submitting an option does not tear down the modal; the next question appears layered on top of the old one.
- No CLI / API workaround documented anywhere.
Pane capture (anonymised)
┃ Done. Tier 3 P9+P10 planning artifacts committed (e375435) and pushed. ...
┃ Going to waiting.
┃
┃ What should I tackle next? Everything remaining needs your call.
┃
┃ 1. Publish [report] + update PR #1
┃ 2. Sub-RPI: P5/P8 LLM challenger
┃ 3. Tier 3 P9 + P10 sub-RPI✓ ← previously selected
┃ 4. Decide M4 [external-tool] nightly policy
┃ 5. Decide P1 FAIL bug treatment
┃ 6. Pre-cache [data file]
┃ 7. Type your own answer
┃ contineu ← my recovery typo
┃
┃ ↑↓ select enter submit esc dismiss ← esc DOES NOT WORK
┃
▣ Orchestrator · Claude Opus 4.7 · 41.5s ← agent is idle
The "esc dismiss" footer hint is lying — esc is bound but does nothing.
What I had to do to recover
Kill the entire OpenCode session via external orchestrator (concierge kill <name>) and re-spawn against the same project directory. Lost only the in-flight Oracle task — committed state on disk was preserved. This should not require killing the whole session.
Cross-references
- #9284 — agent re-asks in loop (closed stale, not fixed). Symptom overlaps but root cause may differ.
- #20095 / #20250 — ESC race (fixed v1.3.3+). I'm on v1.14.50, so this is a new failure mode, not a regression of that fix.
- #11367, #26849, #23515 — open UX issues on the question modal.
- #24988 (shipped v1.14.51) — preserved text selection on question prompts, but does not address dismiss / escape.
Suggested fixes
- Make
Escactually fireQuestion.dismiss()instead of being a no-op (the footer claims it works). - Make
Ctrl-Calways interrupt — current behavior leaves the user with no escape hatch. - When the user is in option-select mode, either route stray keystrokes to the custom-answer field only if they explicitly tab/select into it, or display the typed buffer visibly so users know it's being captured.
- Fully tear down the previous modal before rendering a new question, so a successful submit doesn't visually overlap with the next question.
Activity
simonklee commentedon May 18, 2026
Thanks for reporting this issue. We'll have a look at it.
dawidbednarczyk commentedon May 20, 2026
Hitting this on v1.14.50 from a tmux automation driver — confirming the bug and adding a diagnostic that may help narrow it down.
Reproduction (tmux driver, not interactive)
Driving an opencode session via
tmux send-keys -t <session> Enterto confirm a modal. The Enter byte arrives correctly (opentui maps\r→key.name="return"atpackages/core/src/lib/parse.keypress.ts:268), but the modal does not dismiss and the server logs:(from
packages/opencode/src/question/index.ts:172-175)Diagnostic:
/questionHTTP probe distinguishes orphan from liveThe opencode HTTP server exposes
GET /question(and/permission). When the modal is live, the response is a non-empty array. When the modal is orphaned (server already resolved/rejected, TUI still rendering), the response is[].Confirmed against two sessions on v1.14.50:
GET /question(editing=true, confirm=true)state — see below[](orphan)submit()→Question.reply→log.warn("reply for unknown request")→ no-opThis split (live vs orphan) means there are two distinct failure modes behind the same visible symptom:
pendingMap is empty, TUI is stale. Recovery: re-attach (as TUI permission dialog can become stale: Enter confirm does nothing while /permission returns #28312 documents) or kill+respawn the TUI process.(editing=true, confirm=true)binding trap — neither of the twouseBindingsblocks inpackages/opencode/src/cli/cmd/tui/routes/session/question.tsxhas Enter bound whenstore.editing=trueANDconfirm()=true(block A line 122 requires!confirm(), block B line 198 requires!store.editing). Reachable via mouse click on the Confirm tab while textarea is in editing mode (line 392onMouseDowndoesn't clearediting), or via the keymap rewrite landed in introduce opentui keymap as sole key/cmd engine #26053 (98f5e6e71).Workaround for tmux drivers
The
Escapeclears any stuckeditingflag (Escape is bound in both blocks); theEnterthen fires through block B's Confirm branch. This recovers case (2) but not case (1) — for orphan overlays, a/questionHTTP probe +opencode attach(per #28312) is the only path back.Why upgrading to v1.14.51 does not help
That's the entire diff. The mouse-selection guard doesn't touch Enter, dismiss, or overlay teardown. Confirms the issue persists.
Suggested investigation
/questionbefore routing Enter tosubmit(), orQuestion.reply's "reply for unknown request" path also send a "tear down modal" signal back to the TUI so the orphan overlay self-clears.Happy to file a separate issue if the maintainers prefer to track the binding-trap case (2) separately from the orphan-overlay case (1).
rekram1-node commentedon Jun 23, 2026
Automated: closing question issues.
GitHub Issues are for bug reports and feature requests only — questions / support are no longer tracked here.
If this is a bug or feature request, please open a new issue with the appropriate template.
rekram1-node commentedon Jun 23, 2026
Reopening – this was incorrectly closed by automated question-issue cleanup. Sorry for the noise.
github-actions commentedon Aug 23, 2026
To stay organized issues are automatically closed after 60 days of no activity. If the issue is still relevant please open a new one.