diff --git a/integration-tests/sdk-typescript/subagents.test.ts b/integration-tests/sdk-typescript/subagents.test.ts index 2b8651bab..487e0e7e7 100644 --- a/integration-tests/sdk-typescript/subagents.test.ts +++ b/integration-tests/sdk-typescript/subagents.test.ts @@ -305,7 +305,7 @@ OTHER AGENTS CANNOT: if (isSDKAssistantMessage(message)) { // Check for task tool use in content blocks (main agent calling subagent) - const taskToolBlocks = findToolUseBlocks(message, 'task'); + const taskToolBlocks = findToolUseBlocks(message, 'agent'); if (taskToolBlocks.length > 0) { foundTaskTool = true; taskToolUseId = taskToolBlocks[0].id; @@ -399,7 +399,7 @@ OTHER AGENTS CANNOT: // Check for task tool use (main agent delegating to subagent) const toolUseBlock = message.message.content.find( (block: ContentBlock): block is ToolUseBlock => - block.type === 'tool_use' && block.name === 'task', + block.type === 'tool_use' && block.name === 'agent', ); if (toolUseBlock) { foundTaskTool = true; diff --git a/packages/core/src/permissions/permission-manager.test.ts b/packages/core/src/permissions/permission-manager.test.ts index f7a312f1a..d15f36b25 100644 --- a/packages/core/src/permissions/permission-manager.test.ts +++ b/packages/core/src/permissions/permission-manager.test.ts @@ -49,7 +49,15 @@ describe('resolveToolName', () => { }); it('resolves Agent category', () => { - expect(resolveToolName('Agent')).toBe('task'); + expect(resolveToolName('Agent')).toBe('agent'); + expect(resolveToolName('agent')).toBe('agent'); + expect(resolveToolName('AgentTool')).toBe('agent'); + }); + + it('resolves legacy task aliases to agent', () => { + expect(resolveToolName('task')).toBe('agent'); + expect(resolveToolName('Task')).toBe('agent'); + expect(resolveToolName('TaskTool')).toBe('agent'); }); it('returns unknown names unchanged', () => { @@ -158,7 +166,7 @@ describe('parseRule', () => { it('parses Agent with literal specifier', () => { const r = parseRule('Agent(Explore)'); - expect(r.toolName).toBe('task'); + expect(r.toolName).toBe('agent'); expect(r.specifier).toBe('Explore'); expect(r.specifierKind).toBe('literal'); }); @@ -798,7 +806,7 @@ describe('PermissionManager', () => { it('returns default for unmatched tool', () => { // Note: 'glob' is covered by ReadFileTool via Read meta-category, // so use a tool not in any rule or meta-category - expect(pm.evaluate({ toolName: 'task' })).toBe('default'); + expect(pm.evaluate({ toolName: 'agent' })).toBe('default'); }); it('deny takes precedence over ask and allow', () => { @@ -1294,8 +1302,8 @@ describe('getRuleDisplayName', () => { expect(getRuleDisplayName('web_fetch')).toBe('WebFetch'); }); - it('maps task to "Task" and skill to "Skill"', () => { - expect(getRuleDisplayName('task')).toBe('Task'); + it('maps agent to "Agent" and skill to "Skill"', () => { + expect(getRuleDisplayName('agent')).toBe('Agent'); expect(getRuleDisplayName('skill')).toBe('Skill'); }); @@ -1488,12 +1496,12 @@ describe('buildPermissionRules', () => { expect(rules).toEqual(['Skill(Explore)']); }); - it('generates Task rule with specifier', () => { + it('generates Agent rule with specifier', () => { const rules = buildPermissionRules({ - toolName: 'task', + toolName: 'agent', specifier: 'research', }); - expect(rules).toEqual(['Task(research)']); + expect(rules).toEqual(['Agent(research)']); }); it('falls back to bare display name when no specifier', () => { diff --git a/packages/core/src/permissions/rule-parser.ts b/packages/core/src/permissions/rule-parser.ts index 8667603b4..32c413081 100644 --- a/packages/core/src/permissions/rule-parser.ts +++ b/packages/core/src/permissions/rule-parser.ts @@ -99,10 +99,15 @@ export const TOOL_NAME_ALIASES: Readonly> = { WebSearch: 'web_search', WebSearchTool: 'web_search', - // Task tool - task: 'task', - Task: 'task', - TaskTool: 'task', + // Agent (subagent) tool + agent: 'agent', + Agent: 'agent', + AgentTool: 'agent', + + // Legacy aliases for the agent tool (renamed from "task") + task: 'agent', + Task: 'agent', + TaskTool: 'agent', // Skill tool skill: 'skill', @@ -121,10 +126,6 @@ export const TOOL_NAME_ALIASES: Readonly> = { // Legacy edit tool name replace: 'edit', - - // Agent (subagent) rules — "Agent" is a user-friendly alias for the Task tool. - // "Agent(Explore)" is parsed with toolName = "task" and specifier = "Explore" - Agent: 'task', }; /** @@ -301,7 +302,7 @@ const CANONICAL_TO_RULE_DISPLAY: Readonly> = { web_fetch: 'WebFetch', web_search: 'WebSearch', // Agent / Skill - task: 'Task', + agent: 'Agent', skill: 'Skill', // Others save_memory: 'SaveMemory', diff --git a/packages/core/src/tools/agent.ts b/packages/core/src/tools/agent.ts index 1191bd71a..1b0c1c924 100644 --- a/packages/core/src/tools/agent.ts +++ b/packages/core/src/tools/agent.ts @@ -534,7 +534,7 @@ class AgentToolInvocation extends BaseToolInvocation { } } catch (hookError) { debugLogger.warn( - `[TaskTool] SubagentStart hook failed, continuing execution: ${hookError}`, + `[Agent] SubagentStart hook failed, continuing execution: ${hookError}`, ); } }