From af0d7dc851576c646c30ec298678eb720fef9ac4 Mon Sep 17 00:00:00 2001 From: claude-code-best Date: Sat, 9 May 2026 15:45:20 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20=E5=B0=86=20Agents/Teams=20=E5=B7=A5?= =?UTF-8?q?=E5=85=B7=E7=BA=B3=E5=85=A5=20Tool=20Search=20=E6=8C=89?= =?UTF-8?q?=E9=9C=80=E5=8F=91=E7=8E=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 将 TeamCreate、TeamDelete、SendMessage 从 CORE_TOOLS 移除, 使其成为 deferred 工具,通过 ToolSearch 按需发现以减少 context token。 swarm 模式下 SendMessage 保持 always loaded,TeamCreate/TeamDelete 在 swarm 未启用时调用返回启用提示。 Co-Authored-By: Claude Opus 4.7 --- .../src/tools/SendMessageTool/SendMessageTool.ts | 6 ++++-- .../src/tools/TeamCreateTool/TeamCreateTool.ts | 11 +++++++++-- .../src/tools/TeamDeleteTool/TeamDeleteTool.ts | 11 +++++++++-- .../src/tools/ToolSearchTool/prompt.ts | 2 +- src/constants/__tests__/tools.test.ts | 15 +++++++++++---- src/constants/tools.ts | 4 ---- src/tools.ts | 5 ++--- 7 files changed, 36 insertions(+), 18 deletions(-) diff --git a/packages/builtin-tools/src/tools/SendMessageTool/SendMessageTool.ts b/packages/builtin-tools/src/tools/SendMessageTool/SendMessageTool.ts index 6665dd1f2..82c9a04c3 100644 --- a/packages/builtin-tools/src/tools/SendMessageTool/SendMessageTool.ts +++ b/packages/builtin-tools/src/tools/SendMessageTool/SendMessageTool.ts @@ -553,7 +553,8 @@ async function handlePlanRejection( export const SendMessageTool: Tool = buildTool({ name: SEND_MESSAGE_TOOL_NAME, - searchHint: 'send messages to agent teammates (swarm protocol)', + searchHint: + 'send message to teammate agent, broadcast, inter-agent communication, swarm messaging, agent coordination', maxResultSizeChars: 100_000, userFacingName() { @@ -564,9 +565,10 @@ export const SendMessageTool: Tool = return inputSchema() }, shouldDefer: true, + alwaysLoad: isAgentSwarmsEnabled(), isEnabled() { - return isAgentSwarmsEnabled() + return true }, isReadOnly(input) { diff --git a/packages/builtin-tools/src/tools/TeamCreateTool/TeamCreateTool.ts b/packages/builtin-tools/src/tools/TeamCreateTool/TeamCreateTool.ts index a769325a6..3a2f8aeed 100644 --- a/packages/builtin-tools/src/tools/TeamCreateTool/TeamCreateTool.ts +++ b/packages/builtin-tools/src/tools/TeamCreateTool/TeamCreateTool.ts @@ -73,7 +73,8 @@ function generateUniqueTeamName(providedName: string): string { export const TeamCreateTool: Tool = buildTool({ name: TEAM_CREATE_TOOL_NAME, - searchHint: 'create a multi-agent swarm team', + searchHint: + 'create multi-agent swarm team, collaborate, parallel agents, task distribution, agent coordination, team management', maxResultSizeChars: 100_000, shouldDefer: true, @@ -86,7 +87,7 @@ export const TeamCreateTool: Tool = buildTool({ }, isEnabled() { - return isAgentSwarmsEnabled() + return true }, toAutoClassifierInput(input) { @@ -126,6 +127,12 @@ export const TeamCreateTool: Tool = buildTool({ }, async call(input, context) { + if (!isAgentSwarmsEnabled()) { + throw new Error( + 'Agent Teams 功能未启用。请确保未设置 CLAUDE_CODE_EXPERIMENTAL_AGENT_TEAMS_DISABLED 环境变量。', + ) + } + const { setAppState, getAppState } = context const { team_name, description: _description, agent_type } = input diff --git a/packages/builtin-tools/src/tools/TeamDeleteTool/TeamDeleteTool.ts b/packages/builtin-tools/src/tools/TeamDeleteTool/TeamDeleteTool.ts index f7f3c7247..5ad18c142 100644 --- a/packages/builtin-tools/src/tools/TeamDeleteTool/TeamDeleteTool.ts +++ b/packages/builtin-tools/src/tools/TeamDeleteTool/TeamDeleteTool.ts @@ -50,7 +50,8 @@ export type Input = z.infer export const TeamDeleteTool: Tool = buildTool({ name: TEAM_DELETE_TOOL_NAME, - searchHint: 'disband a swarm team and clean up', + searchHint: + 'disband delete swarm team cleanup, remove team, end team collaboration, cleanup team resources', maxResultSizeChars: 100_000, shouldDefer: true, @@ -63,7 +64,7 @@ export const TeamDeleteTool: Tool = buildTool({ }, isEnabled() { - return isAgentSwarmsEnabled() + return true }, async description() { @@ -88,6 +89,12 @@ export const TeamDeleteTool: Tool = buildTool({ }, async call(input, context) { + if (!isAgentSwarmsEnabled()) { + throw new Error( + 'Agent Teams 功能未启用。请确保未设置 CLAUDE_CODE_EXPERIMENTAL_AGENT_TEAMS_DISABLED 环境变量。', + ) + } + const { setAppState, getAppState } = context const appState = getAppState() const teamName = appState.teamContext?.teamName diff --git a/packages/builtin-tools/src/tools/ToolSearchTool/prompt.ts b/packages/builtin-tools/src/tools/ToolSearchTool/prompt.ts index 91b5973cd..a5be1e4a6 100644 --- a/packages/builtin-tools/src/tools/ToolSearchTool/prompt.ts +++ b/packages/builtin-tools/src/tools/ToolSearchTool/prompt.ts @@ -6,7 +6,7 @@ export { TOOL_SEARCH_TOOL_NAME } from './constants.js' import { TOOL_SEARCH_TOOL_NAME } from './constants.js' -const PROMPT_HEAD = `Search for deferred tools by name or keyword. LOW PRIORITY — only use this tool when no core tool can accomplish the task. Core tools (Read, Edit, Write, Bash, Glob, Grep, Agent, WebFetch, WebSearch, Skill) are always available and should be used directly. This tool is only for discovering additional capabilities like MCP tools, cron scheduling, worktree management, etc. +const PROMPT_HEAD = `Search for deferred tools by name or keyword. LOW PRIORITY — only use this tool when no core tool can accomplish the task. Core tools (Read, Edit, Write, Bash, Glob, Grep, Agent, WebFetch, WebSearch, Skill) are always available and should be used directly. This tool is for discovering additional capabilities like MCP tools, cron scheduling, worktree management, agent teams (TeamCreate, TeamDelete, SendMessage), etc. ` diff --git a/src/constants/__tests__/tools.test.ts b/src/constants/__tests__/tools.test.ts index 09fe5f3d8..b49da17a4 100644 --- a/src/constants/__tests__/tools.test.ts +++ b/src/constants/__tests__/tools.test.ts @@ -52,8 +52,8 @@ function makeTool(overrides: Partial = {}): MockTool { describe('CORE_TOOLS', () => { test('contains expected number of tools', () => { - // 7 SHELL_TOOL_NAMES + 22 independent tool names - expect(CORE_TOOLS.size).toBeGreaterThanOrEqual(29) + // 7 SHELL_TOOL_NAMES + 19 independent tool names + expect(CORE_TOOLS.size).toBeGreaterThanOrEqual(26) }) test('contains key core tool names', () => { @@ -72,8 +72,6 @@ describe('CORE_TOOLS', () => { 'Sleep', 'LSP', 'Skill', - 'TeamCreate', - 'TeamDelete', 'TaskCreate', 'TaskGet', 'TaskUpdate', @@ -124,6 +122,15 @@ describe('isDeferredTool', () => { expect(isDeferredTool(tool as never)).toBe(true) }) + test('returns true for agent/team tools (TeamCreate, TeamDelete, SendMessage)', () => { + for (const name of ['TeamCreate', 'TeamDelete', 'SendMessage']) { + const tool = makeTool({ name }) + expect(isDeferredTool(tool as never), `${name} should be deferred`).toBe( + true, + ) + } + }) + test('returns true for MCP tools', () => { const tool = makeTool({ name: 'mcp__server__action', isMcp: true }) expect(isDeferredTool(tool as never)).toBe(true) diff --git a/src/constants/tools.ts b/src/constants/tools.ts index 0c70f0e2d..071d605b7 100644 --- a/src/constants/tools.ts +++ b/src/constants/tools.ts @@ -135,10 +135,6 @@ export const CORE_TOOLS = new Set([ // Agent & interaction AGENT_TOOL_NAME, // 'Agent' ASK_USER_QUESTION_TOOL_NAME, // 'AskUserQuestion' - SEND_MESSAGE_TOOL_NAME, // 'SendMessage' - // Team (swarm) - TEAM_CREATE_TOOL_NAME, // 'TeamCreate' - TEAM_DELETE_TOOL_NAME, // 'TeamDelete' // Task management TASK_OUTPUT_TOOL_NAME, // 'TaskOutput' TASK_STOP_TOOL_NAME, // 'TaskStop' diff --git a/src/tools.ts b/src/tools.ts index ebcff1ac8..ed9200b4e 100644 --- a/src/tools.ts +++ b/src/tools.ts @@ -247,9 +247,8 @@ export function getAllBaseTools(): Tools { ...(isWorktreeModeEnabled() ? [EnterWorktreeTool, ExitWorktreeTool] : []), getSendMessageTool(), ...(ListPeersTool ? [ListPeersTool] : []), - ...(isAgentSwarmsEnabled() - ? [getTeamCreateTool(), getTeamDeleteTool()] - : []), + getTeamCreateTool(), + getTeamDeleteTool(), ...(VerifyPlanExecutionTool ? [VerifyPlanExecutionTool] : []), ...(process.env.USER_TYPE === 'ant' && REPLTool ? [REPLTool] : []), ...(WorkflowTool ? [WorkflowTool] : []),