anthropics / anthropics/claude-agent-sdk-typescript
canUseTool drops `requires_user_interaction`, so SDK hosts cannot honour `anthropic/requiresUserInteraction`
- Lingua principale
- Shell
- Stelle
- 1.8k
- Fork
- 226
- Metriche di merge delle PR
- Nessuna PR unita negli ultimi 30g
Descrizione
## Summary
An MCP server can mark a tool with `_meta["anthropic/requiresUserInteraction"]: true`, which is documented to make Claude Code prompt on every call and **not** offer a remembering option.
The CLI sets that flag and sends it on the wire: the `can_use_tool` control request carries `requires_user_interaction: true`. But `processControlRequest` does not map it into the options object it passes to the host's `canUseTool` callback, and `CanUseTool`'s type does not declare it. An SDK host therefore has no supported way to know that this particular call must not be offered an "always allow" affordance.
## Evidence
Captured by patching `sdk.mjs` to log `e.request` for every `can_use_tool` control request, then calling one annotated MCP tool and one ordinary Bash command (tool names sanitised):
```json
{
"subtype": "can_use_tool",
"tool_name": "mcp__example__write_tool",
"display_name": "Write Tool",
"input": { "...": "..." },
"matched_ask_rule": { "source": "userSettings", "tool_name": "mcp__example__write_tool" },
"tool_use_id": "toolu_…",
"requires_user_interaction": true
}
```
```json
{
"subtype": "can_use_tool",
"tool_name": "Bash",
"input": { "command": "ls -la /tmp" },
"permission_suggestions": [ { "type": "addRules", "rules": [ … ], "behavior": "allow", "destination": "localSettings" } ],
"decision_reason_type": "subcommandResults",
"tool_use_id": "toolu_…"
}
```
Note the annotated tool has `requires_user_interaction: true` and **no** `permission_suggestions`, while the ordinary tool has suggestions and no flag. The CLI's behaviour is correct in both directions.
## Where
`sdk.mjs`, `Query.processControlRequest` — the `can_use_tool` branch maps `permission_suggestions`, `blocked_path`, `decision_reason`, `title`, `display_name`, `description`, `tool_use_id`, `agent_id`, `request_id` and `matched_ask_rule`, and omits `requires_user_interaction`.
`sdk.d.ts` — the field is declared, but on the remote-sidebar payload type (documented there as *"True when one-tap Approve/Deny must not be offered"*), not on `CanUseTool`'s options.
## Impact
Any SDK-based host that renders its own permission UI will offer a remembering option for a tool whose whole point is that consent cannot be remembered. Observed downstream in `@agentclientprotocol/claude-agent-acp`, where the prompt for an annotated tool shows Deny / Allow Once / **Always Allow**.
The gate itself holds — the CLI ignores the resulting allow rule and re-prompts — so this is a UI-truthfulness bug rather than a security hole. But a button that offers to remember an answer, silently fails to, and reappears on every call trains people to click it without reading, which is the opposite of what a consent gate is for.
## Suggested fix
Map the field through and declare it:
```js
...e.request.requires_user_interaction && { requiresUserInteraction: true },
```
```ts
/** True when this call must not be offered a remembered/"always allow" option. */
requiresUserInteraction?: boolean;
```
## Versions
- `@anthropic-ai/claude-agent-sdk` 0.3.232 (bundled CLI 2.1.232)
- host: `@agentclientprotocol/claude-agent-acp` 0.68.0 in Zed
Guida per i contributori
Nessuna guida per i contributori indicizzata per questo repository
Valutazione
Questa issue non è ancora stata valutata.