| 1 | //! Tool wrapper for executing multiple tool calls in parallel. |
| 2 | //! |
| 3 | //! NOTE: this meta-tool is intentionally no longer registered with the |
| 4 | //! agent (see `ToolRegistryBuilder::with_parallel_tool`). DeepSeek-V4 |
| 5 | //! supports native parallel `tool_calls` in a single assistant turn, and |
| 6 | //! advertising the OpenAI-internal name `multi_tool_use.parallel` made |
| 7 | //! the model hallucinate ChatGPT-style XML wrappers. The struct stays |
| 8 | //! around so the engine compatibility dispatcher and historical sessions |
| 9 | //! still resolve it cleanly. |
| 10 | |
| 11 | use super::spec::{ |
| 12 | ApprovalRequirement, ToolCapability, ToolContext, ToolError, ToolResult, ToolSpec, |
| 13 | }; |
| 14 | use async_trait::async_trait; |
| 15 | use serde_json::{Value, json}; |
| 16 | |
| 17 | #[allow(dead_code)] |
| 18 | pub struct MultiToolUseParallelTool; |
| 19 | |
| 20 | #[async_trait] |
| 21 | impl ToolSpec for MultiToolUseParallelTool { |
| 22 | fn name(&self) -> &'static str { |
| 23 | "multi_tool_use.parallel" |
| 24 | } |
| 25 | |
| 26 | fn description(&self) -> &'static str { |
| 27 | "Execute multiple tool calls in parallel and return their results." |
| 28 | } |
| 29 | |
| 30 | fn input_schema(&self) -> Value { |
| 31 | json!({ |
| 32 | "type": "object", |
| 33 | "properties": { |
| 34 | "tool_uses": { |
| 35 | "type": "array", |
| 36 | "items": { |
| 37 | "type": "object", |
| 38 | "properties": { |
| 39 | "recipient_name": { "type": "string" }, |
| 40 | "parameters": { "type": "object" } |
| 41 | }, |
| 42 | "required": ["recipient_name", "parameters"] |
| 43 | } |
| 44 | } |
| 45 | }, |
| 46 | "required": ["tool_uses"] |
| 47 | }) |
| 48 | } |
| 49 | |
| 50 | fn capabilities(&self) -> Vec<ToolCapability> { |
| 51 | vec![ToolCapability::ReadOnly] |
| 52 | } |
| 53 | |
| 54 | fn approval_requirement(&self) -> ApprovalRequirement { |
| 55 | ApprovalRequirement::Auto |
| 56 | } |
| 57 | |
| 58 | async fn execute( |
| 59 | &self, |
| 60 | _input: Value, |
| 61 | _context: &ToolContext, |
| 62 | ) -> Result<ToolResult, ToolError> { |
| 63 | Err(ToolError::execution_failed( |
| 64 | "multi_tool_use.parallel must be handled by the engine", |
| 65 | )) |
| 66 | } |
| 67 | } |
| 68 |