`--allow-all` read permissions leak to the UI dispatcher and wedge the TUI (no input box) on `-i`/`--resume` startup
- Dominant language
- Shell
- Stars
- 11.2k
- Forks
- 1.9k
- Avg merge
- 14h 16m
- Merged PRs (30d)
- 6
Description
# Bug: `--allow-all` read permissions leak to the UI dispatcher and wedge the TUI (no input box)
## Summary
When launching a session non-interactively (`copilot --allow-all … -i "@"`) **or** resuming one (`copilot --allow-all --resume= …`), `read`-kind permission requests that should be auto-approved at the session/wire layer are instead **surfaced to the UI dispatcher**. The TUI comes up and renders/scrolls, but there is **no input box and the session is completely unresponsive to keyboard input**. No work is performed. Starting a session plain-interactively (`copilot`, then typing/pasting the prompt) does **not** reproduce it.
## Environment
- GitHub Copilot CLI **1.0.63** (`copilot/1.0.63 (win32 v24.16.0)`)
- OS: Windows (Windows Terminal; tabs spawned via `wt -w 0 new-tab … pwsh -NoLogo -EncodedCommand …`)
- Folder already trusted: `~/.copilot/config.json` → `"trustedFolders": ["D:\\Code"]` (both working dirs are under `D:\Code`, so this is **not** a first-time folder-trust prompt)
- Possibly-relevant experiment flights in `config.json` (NOT confirmed as the cause — listed only as leads): `cfdic-spawn`, `cli_aa_c`, `cli_aa_monitor_t`, and params `copilot_cli_shell_spawn_backend: true`, `copilot_cli_remove_parallel_tool_prompt: true`.
## Impact
- Any automation that launches/resumes Copilot non-interactively with `--allow-all -i "@file"` / `--resume` produces a dead, input-less TUI.
- Hit **both** a freshly-launched tab and a `--resume` tab in the same session. Repeating via the `/resume` command reproduced it as well.
- Only workaround found: start `copilot` interactively (no `-i`, no `--resume`) and paste the prompt by hand.
## Steps to reproduce
1. In a trusted folder (folder already in `trustedFolders`), run either:
- Launch: `copilot --allow-all --name --reasoning-effort max -i "@.md"`
- Resume: `copilot --allow-all --resume= --reasoning-effort high -i "@.md"`
2. On startup the CLI prompts to add the directory to the allow list (unexpected — `--allow-all` is set and the folder is already trusted). Approve it.
3. The session UI appears and scrolls, but there is **no input box** and it accepts no keyboard input. No agent work happens.
Expected: with `--allow-all`, permission requests are auto-approved at the session/wire layer and the session is interactive (or, for `-i`, immediately starts working on the seeded prompt).
Actual: `read` permission requests are dispatched to the UI layer, which never yields an interactive input box; the session is wedged.
## Evidence (from a `--resume` tab's process log)
The error fires **repeatedly** through startup — at foreground-session registration, extension/tool registration, and every MCP client connect:
```
15:27:35.428 [INFO] Welcome !
15:27:35.434 [ERROR] PermissionRequestPrompt: kind='read' surfaced to UI dispatcher. Expected to be auto-approved at the session or wire layer.
15:27:35.435 [INFO] Unregistering foreground session:
15:27:35.436 [INFO] Registering foreground session:
15:27:35.441 [ERROR] PermissionRequestPrompt: kind='read' surfaced to UI dispatcher. …
15:27:35.821 [ERROR] PermissionRequestPrompt: kind='read' surfaced to UI dispatcher. …
15:27:35.912 [ERROR] PermissionRequestPrompt: kind='read' surfaced to UI dispatcher. …
15:27:36.263 [ERROR] PermissionRequestPrompt: kind='read' surfaced to UI dispatcher. … (during MCP client startup)
15:27:38.117 [ERROR] PermissionRequestPrompt: kind='read' surfaced to UI dispatcher. …
15:27:38.214 [ERROR] PermissionRequestPrompt: kind='read' surfaced to UI dispatcher. …
15:27:38.714 [ERROR] PermissionRequestPrompt: kind='read' surfaced to UI dispatcher. …
15:27:39.091 [ERROR] PermissionRequestPrompt: kind='read' surfaced to UI dispatcher. …
15:27:39.276 [ERROR] PermissionRequestPrompt: kind='read' surfaced to UI dispatcher. …
```
The log message itself states the invariant that's being violated: these reads were **"Expected to be auto-approved at the session or wire layer."** With `--allow-all` set, none of these should reach the UI dispatcher.
(Same symptom independently observed on the freshly-launched tab for a different worktree under `D:\Code`.)
## Cross-session falsification check
Counting genuine runtime occurrences (anchored on the ISO-timestamped `[ERROR]` line) across all sessions on this machine this morning gives a clean split — the error is present in every wedged tab and absent from every working session:
| Session | startup | true error count | outcome |
|---|---|---|---|
| A (long-running) | interactive | 0 | working |
| B — 3 auto-launch attempts | `--allow-all -i "@file"` | 17 / 36 / 45 | wedged |
| C — 3 auto-launch/resume attempts | `--allow-all --resume -i "@file"` | 15 / 36 / 33 | wedged |
| B — manual recovery | interactive (paste prompt) | 0 | working |
| C — manual recovery | interactive (paste prompt) | 0 | working |
| A — later, same session | interactive | 0 | working |
100% of wedged tabs emit the error; 0% of working sessions do. The discriminating factor is **non-interactive startup** (`-i "@file"` / `--resume`) vs plain interactive. (Caveat: this is tight correlation across one machine / one morning, not a traced causal mechanism — no stack trace was captured showing the input box being suppressed.)
## Likely cause / hypothesis
A regression in the permission auto-approval path: under `--allow-all` (and/or the `cfdic-spawn` / `copilot_cli_shell_spawn_backend` experiment), `read`-kind `PermissionRequestPrompt`s are not being satisfied at the session/wire layer and fall through to the interactive UI dispatcher. Because these fire during non-interactive startup (`-i`/`--resume`), the dispatcher ends up in a state with no usable input affordance, leaving the TUI rendered but dead.
## Workaround
Start `copilot` interactively (no `-i`, no `--resume`) and paste the prompt manually; rename the session afterward if needed. This avoids the wedged dispatcher.
## Asks
- Ensure `read` permissions are auto-approved at the session/wire layer (especially under `--allow-all`) and never surface to the UI dispatcher during non-interactive (`-i` / `--resume`) startup.
- If the `cfdic-spawn` / `copilot_cli_shell_spawn_backend` flight is implicated, consider gating/rolling it back while the auto-approve path is fixed.
Contributor guide
Assessment
This issue has not been assessed yet.