google-gemini / google-gemini/gemini-cli
cli_help subagent hangs for exactly 3 minutes on any CLI meta-question (unbounded thinkingBudget, no per-turn timeout)
- Dominant language
- TypeScript
- Stars
- 107k
- Forks
- 14.6k
- Avg merge
- 2d 3h
- Merged PRs (30d)
- 45
Description
### Description
The built-in `cli_help` local subagent (invoked automatically whenever the user asks a meta-question about the CLI itself — e.g. "how do I upgrade", "check my version", "is something wrong with my account") reliably hangs for exactly 3 minutes, then either times out or loops on an empty tool response, instead of answering. Regular content questions (anything not about the CLI itself) answer instantly and correctly, including in headless `-p` mode — so this is isolated to the `cli_help` code path, not the API key, account, or model access in general.
### Environment
- Gemini CLI version: 0.59.0 (npm global install, `@google/gemini-cli`)
- OS: macOS (Darwin 25.6.0, arm64 / Apple Silicon)
- Node: v26.8.1
- Auth type: `gemini-api-key` (AI Studio key)
- Configured model (`ui`/`model.name` in settings.json): `gemini-3.1-flash-lite`
### Steps to reproduce
1. Start `gemini` in interactive mode with auth type `gemini-api-key`.
2. Ask any question that the CLI classifies as being about itself, e.g.:
- "how do I upgrade gemini-cli to the latest version"
- "how do I check to see if gemini is running the latest version"
- "is there a problem with my gemini cli account?"
3. Observe the CLI invoke the `invoke_agent` tool with `cli_help`.
4. Wait.
### Expected behavior
`cli_help` reads local bundled docs (via `get_internal_docs`) and returns a short answer within a few seconds, same as it does for the equivalent question asked directly of the base model.
### Actual behavior
The subagent run never completes normally. Captured directly from `~/.gemini/tmp//chats/session-*.jsonl`:
```
functionResponse.output: "Subagent 'cli_help' finished.\nTermination Reason: TIMEOUT\nResult:\nAgent timed out after 3 m[inutes]..."
```
and, on a separate occurrence:
```
gemini -> toolCalls: [invoke_agent(cli_help, ...)]
user -> [System: You successfully executed a tool but returned an empty response. Please analyze the tool output and explain your progress or final answer.]
info -> Request cancelled.
```
This second pattern repeats (empty response → CLI re-prompts itself → empty response again) until the user cancels.
### Root cause (from reading the installed bundle)
`packages/core/dist/src/agents/cli-help-agent.js` (as bundled in `chunk-YSBB75DZ.js` of the npm package) defines:
```js
var CliHelpAgent = (context2) => ({
name: "cli_help",
kind: "local",
modelConfig: {
model: GEMINI_MODEL_ALIAS_FLASH, // resolves to the "flash" alias
generateContentConfig: {
temperature: 0.1,
topP: 0.95,
thinkingConfig: {
includeThoughts: true,
thinkingBudget: -1 // unbounded / dynamic thinking budget
}
}
},
runConfig: {
maxTimeMinutes: 3,
maxTurns: 10
},
toolConfig: { tools: [new GetInternalDocsTool(context2.messageBus)] },
...
});
```
Two things stand out:
1. **`thinkingBudget: -1`** gives the model no cap on how long it can "think" before it has to emit a tool call (`get_internal_docs` or `complete_task`). There is no shorter per-turn timeout — the *only* backstop is the coarse `maxTimeMinutes: 3` on the whole agent run. If the model gets stuck reasoning without emitting a call (a pattern reported elsewhere for preview/flash models, see Related issues), the entire 3-minute budget is silently consumed on a single turn, which matches the exact `TIMEOUT after 3 minutes` observed.
2. **`model: GEMINI_MODEL_ALIAS_FLASH`** (`"flash"`) is hardcoded independent of the user's configured model. Depending on preview-model entitlement (`hasAccessToPreview`), `resolveClassifierModel` can resolve this to `gemini-3-flash-preview` rather than `gemini-2.5-flash` — i.e. `cli_help` can end up calling a preview model even when the user's own chat sessions are pinned to a stable model. This matters because the hangs/retry-loops referenced below are specifically reported against preview models.
### Workaround
Disable the subagent via `~/.gemini/settings.json`:
```json
{
"agents": {
"overrides": {
"cli_help": { "enabled": false }
}
}
}
```
After this change, the same previously-hanging question (e.g. "how do I upgrade gemini-cli") is answered directly by the base model in a few seconds.
### Suggested fix
- Add a shorter internal per-turn/per-call timeout to the `cli_help` (and likely other local subagents using `thinkingBudget: -1`) run loop, distinct from the overall `maxTimeMinutes`, so a single stuck turn doesn't burn the whole budget silently.
- Reconsider hardcoding `GEMINI_MODEL_ALIAS_FLASH` for `cli_help` without regard to whether the account has stable preview-model access, given the preview-model hang reports below.
- On timeout, surface a visible error/status to the user immediately rather than looping the outer CLI into "you returned an empty response" retries.
### Related issues
These look like the same underlying "stuck thinking / retry loop" bug class, previously reported without being traced to `cli_help` specifically. Both were closed "not planned," likely due to being intermittent and hard to reproduce on demand — this report includes the first reliable, deterministic repro steps (any CLI meta-question) tied to a specific code path.
- #26126 — "Stuck at thinking"
- #22415 — "CLI hangs indefinitely on 'This is taking a bit longer' with gemini-3.1-pro-preview (Possible retry loop)"
- #18030 — "API calls hang for 5 minutes (default node timeout) without retry"
- #22241 — "Gemini CLI hangs indefinitely on all API calls with Google One AI Ultra subscription (OAuth)"
- #16567 — "Gemini CLI consistently hangs when running a command in non-interactive mode"
Contributor guide
Research direction
Start with packages/core/dist/src/agents/cli-help-agent.js in chunk-YSBB75DZ.js and trace the local-subagent run loop, especially thinkingBudget, maxTimeMinutes, and timeout handling. Reproduce the issue with a CLI meta-question and inspect the empty-response retry path. Done means a stuck turn is bounded separately and timeout is surfaced without repeatedly re-prompting the outer CLI.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- node.js, typescript
- Domain
- ai, cli
- Issue type
- Bug
- Difficulty
- 4/5
- Estimated time
- 3-5 days
- Activity status
- Active
- Clarity
- Mostly clear
- Newbie friendliness
- 48/100