From 1c8abcb23a4c0fd666fd8131ab1604ce38cd9028 Mon Sep 17 00:00:00 2001 From: wassname <1103714+wassname@users.noreply.github.com> Date: Fri, 2 Oct 2026 15:27:00 +0800 Subject: [PATCH] Let planning consult helper subagents; workers still wait for Ready Planning blocked every subagent launch, so oracles and scouts could not run before Ready. Now only OpenGoalWorker and project.* are blocked in planning; pause still blocks all launches. Co-Authored-By: PI[gpt-6-sol] <288921227+claudypoo@users.noreply.github.com> --- src/index.ts | 3 ++- test/goals.test.ts | 4 +++- 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/src/index.ts b/src/index.ts index dc2933e..abd0ac9 100644 --- a/src/index.ts +++ b/src/index.ts @@ -701,7 +701,8 @@ export default function mainSupervisor(pi: ExtensionAPI) { // Stock owns helper contracts and capabilities. Inspection and cancellation stay available. if (event.toolName === "subagent" && typeof action === "string" && ["list", "get", "models", "guide", "status", "children.list", "project.status", "stop", "interrupt"].includes(action)) return; const nativeWorkerControl = event.toolName === "OpenGoalWorker" || typeof action === "string" && action.startsWith("project."); - if (["planning", "paused"].includes(state.mode)) return { block: true, reason: goalToolBlocked(state.mode) }; + // Planning may consult helpers (oracles, scouts); workers wait for Ready. Pause blocks all launches. + if (state.mode === "paused" || (state.mode === "planning" && nativeWorkerControl)) return { block: true, reason: goalToolBlocked(state.mode) }; if (nativeWorkerControl && (state.child || state.mode === "solo")) return { block: true, reason: goalToolBlocked(state.child ? "worker" : state.mode) }; }); diff --git a/test/goals.test.ts b/test/goals.test.ts index 3f2734c..a0b59a1 100644 --- a/test/goals.test.ts +++ b/test/goals.test.ts @@ -208,8 +208,10 @@ it.each(["menu", "command"])("enters planning conversation through %s without a expect(f.ctx.ui.editor).toHaveBeenCalledTimes(route === "menu" ? 1 : 0); expect(f.messages).toHaveLength(1); expect(f.messages[0].message.content).toContain(route === "menu" ? "Initial idea: supplied instructions" : "Use the existing conversation"); - expect(f.hooks.get("tool_call")({ toolName: "subagent" }).block).toBe(true); + expect(f.hooks.get("tool_call")({ toolName: "subagent", input: { agent: "oracle", task: "brief" } })).toBeUndefined(); expect(f.hooks.get("tool_call")({ toolName: "subagent", input: { action: "status" } })).toBeUndefined(); + expect(f.hooks.get("tool_call")({ toolName: "subagent", input: { action: "project.open" } }).block).toBe(true); + expect(f.hooks.get("tool_call")({ toolName: "OpenGoalWorker", input: { task: "work" } }).block).toBe(true); }); it("cancelled menu New creates nothing and sends nothing", async () => {