{"record":{"id":"97eec89ad8edbadf","repo":"zed-industries/zed","slug":"failed-to-send-tool-call-decision-prompt-error","errorCode":null,"errorMessage":"Failed to send tool call decision prompt: {error}","messagePattern":"Failed to send tool call decision prompt: (.+?)","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"crates/agent/src/thread.rs","lineNumber":6368,"sourceCode":"            if let Some(message) = message {\n                fields = fields.content(vec![acp::ToolCallContent::from(message)]);\n            }\n\n            let (response_tx, response_rx) = oneshot::channel();\n            if let Err(error) = stream\n                .0\n                .unbounded_send(Ok(ThreadEvent::ToolCallAuthorization(\n                    ToolCallAuthorization {\n                        tool_call: acp::ToolCallUpdate::new(tool_call_id.clone(), fields),\n                        options,\n                        response: response_tx,\n                        context: None,\n                        kind: acp_thread::AuthorizationKind::ActionChoice,\n                    },\n                )))\n            {\n                log::error!(\"Failed to send tool call decision prompt: {error}\");\n                return Err(anyhow!(\"Failed to send tool call decision prompt: {error}\"));\n            }\n\n            let outcome = response_rx\n                .await\n                .map_err(|_| anyhow!(\"authorization channel closed\"))?;\n            ensure_tool_call_authorization_not_interrupted(&outcome)?;\n            Ok(outcome.option_id)\n        })\n    }\n\n    /// Prompts the user for authorization.\n    ///\n    /// When `check_settings` is `Some`, this gate is settings-driven: the\n    /// settings are evaluated up-front (an Allow or Deny result resolves the\n    /// task immediately without prompting), and while a prompt is pending a\n    /// `SettingsStore` subscription watches for changes. A subsequent Allow\n    /// or Deny dismisses the prompt UI and resolves the task without user\n    /// interaction.","sourceCodeStart":6350,"sourceCodeEnd":6386,"githubUrl":"https://github.com/zed-industries/zed/blob/bc538def4545534201bbfcac4e95ac34ea6501b6/crates/agent/src/thread.rs#L6350-L6386","documentation":"For tool calls that need an explicit decision, the thread sends a ToolCallAuthorization event with ActionChoice options; if that send fails, the event receiver is gone and this error wraps the failure. The decision prompt is undeliverable, so the gated action fails.","triggerScenarios":"The thread's event consumer is dropped at the moment a tool call decision prompt (for example a continue/stop choice) is being sent.","commonSituations":"Closing the UI exactly when a decision is requested; client disconnects; embedding code scoping the event receiver too narrowly.","solutions":["Hold the ThreadEvent receiver until the thread is finished","Handle the error as cancellation and abort the pending tool call","Re-create the session and resend if the user still wants the action","Cancel the thread before closing the UI so decision prompts resolve as cancelled turns"],"exampleFix":null,"handlingStrategy":"try-catch","validationCode":null,"typeGuard":null,"tryCatchPattern":"if let Err(err) = decision_prompt_result {\n    if err.to_string().starts_with(\"Failed to send tool call decision prompt\") {\n        // Event consumer is gone: treat as cancellation of the gated action.\n        abort_pending_tool_call();\n        return Ok(());\n    }\n    return Err(err);\n}","preventionTips":["Hold the ThreadEvent receiver until the thread is finished","Cancel the thread before closing the UI so decision prompts resolve as cancelled turns","In embedding code, do not scope the event receiver to a shorter task than the thread","Answer or explicitly deny pending decision prompts during teardown"],"tags":["rust","agent","tools","authorization","channel","lifecycle"],"backgroundTag":null,"analyzedSha":"bc538def4545534201bbfcac4e95ac34ea6501b6","analyzedAt":"2026-08-16T07:30:46.435Z","schemaVersion":2},"datasetVersion":"2026-08-16T08:17:34.114Z"}