diff --git a/src/cli/components/SubagentGroupDisplay.tsx b/src/cli/components/SubagentGroupDisplay.tsx index a0ca77d..24a36c7 100644 --- a/src/cli/components/SubagentGroupDisplay.tsx +++ b/src/cli/components/SubagentGroupDisplay.tsx @@ -340,8 +340,12 @@ export const SubagentGroupDisplay = memo(() => { } }); + // Hide silent subagents (e.g. init) — they handle user notifications + // via their own mechanisms (e.g. EventMessage). + const visible = agents.filter((a) => !a.silent); + // Don't render if no agents - if (agents.length === 0) { + if (visible.length === 0) { return null; } @@ -349,24 +353,24 @@ export const SubagentGroupDisplay = memo(() => { // This ensures consistent behavior - when we disable animation, we also simplify the view const condensed = !shouldAnimate; - const allCompleted = agents.every( + const allCompleted = visible.every( (a) => a.status === "completed" || a.status === "error", ); - const hasErrors = agents.some((a) => a.status === "error"); + const hasErrors = visible.some((a) => a.status === "error"); return ( - {agents.map((agent, index) => ( + {visible.map((agent, index) => ( diff --git a/src/cli/helpers/subagentState.ts b/src/cli/helpers/subagentState.ts index 82ce334..3fc7849 100644 --- a/src/cli/helpers/subagentState.ts +++ b/src/cli/helpers/subagentState.ts @@ -30,6 +30,7 @@ export interface SubagentState { startTime: number; toolCallId?: string; // Links this subagent to its parent Task tool call isBackground?: boolean; // True if running in background (fire-and-forget) + silent?: boolean; // True if this subagent should be hidden from SubagentGroupDisplay } interface SubagentStore { @@ -108,6 +109,7 @@ export function registerSubagent( description: string, toolCallId?: string, isBackground?: boolean, + silent?: boolean, ): void { // Capitalize type for display (explore -> Explore) const displayType = type.charAt(0).toUpperCase() + type.slice(1); @@ -124,6 +126,7 @@ export function registerSubagent( startTime: Date.now(), toolCallId, isBackground, + silent, }; store.agents.set(id, agent); diff --git a/src/tools/impl/Task.ts b/src/tools/impl/Task.ts index 730572c..ab79596 100644 --- a/src/tools/impl/Task.ts +++ b/src/tools/impl/Task.ts @@ -66,6 +66,11 @@ export interface SpawnBackgroundSubagentTaskArgs { existingAgentId?: string; existingConversationId?: string; maxTurns?: number; + /** + * When true, skip injecting the completion notification into the primary + * agent's message queue and hide from SubagentGroupDisplay. + */ + silentCompletion?: boolean; /** * Optional dependency overrides for tests. * Production callers should not provide this. @@ -191,6 +196,7 @@ export function spawnBackgroundSubagentTask( existingAgentId, existingConversationId, maxTurns, + silentCompletion, deps, } = args; @@ -208,7 +214,14 @@ export function spawnBackgroundSubagentTask( deps?.getSubagentSnapshotImpl ?? getSubagentSnapshot; const subagentId = generateSubagentIdFn(); - registerSubagentFn(subagentId, subagentType, description, toolCallId, true); + registerSubagentFn( + subagentId, + subagentType, + description, + toolCallId, + true, + silentCompletion, + ); const taskId = getNextTaskId(); const outputFile = createBackgroundOutputFile(taskId);