From 102b754f1e087d9e4bf986a5629210f00453f0ef Mon Sep 17 00:00:00 2001 From: ismeth Date: Tue, 3 Mar 2026 13:21:40 +0100 Subject: [PATCH] fix(athena): remove athena primary from delegation list and switch_agent targets Athena primary should not be routable via switch_agent or appear in the delegation table. Only athena-junior (subagent) remains delegatable via task(). - Remove athena from ALLOWED_AGENTS and DESCRIPTION in switch-agent tool - Remove ATHENA_PROMPT_METADATA from agentMetadata, agent.ts, barrel export - Update switch-agent test to assert athena rejection - Remove ATHENA_PROMPT_METADATA test block --- .../athena/athena-config-injection.test.ts | 53 +------------------ src/agents/athena/index.ts | 2 +- src/tools/switch-agent/tools.test.ts | 14 +++-- src/tools/switch-agent/tools.ts | 4 +- 4 files changed, 10 insertions(+), 63 deletions(-) diff --git a/src/agents/athena/athena-config-injection.test.ts b/src/agents/athena/athena-config-injection.test.ts index 2c5606cdb..397f2de62 100644 --- a/src/agents/athena/athena-config-injection.test.ts +++ b/src/agents/athena/athena-config-injection.test.ts @@ -1,7 +1,7 @@ /// import { describe, expect, it } from "bun:test" -import { createAthenaAgent, ATHENA_PROMPT_METADATA } from "./agent" +import { createAthenaAgent } from "./agent" import { ATHENA_JUNIOR_PROMPT_METADATA } from "./athena-junior-agent" import { ATHENA_NON_INTERACTIVE_PROMPT } from "./non-interactive-prompt" @@ -163,57 +163,6 @@ describe("Athena-Junior prompt metadata", () => { }) }) -describe("Athena prompt metadata", () => { - describe("#given ATHENA_PROMPT_METADATA", () => { - describe("#when checking triggers", () => { - it("#then includes a Multi-model council trigger", () => { - const hasCouncilTrigger = ATHENA_PROMPT_METADATA.triggers.some((t) => - t.domain.includes("Multi-model council"), - ) - expect(hasCouncilTrigger).toBe(true) - }) - }) - - describe("#when checking useWhen entries", () => { - it("#then includes an entry mentioning tradeoffs", () => { - const hasTradeoffs = ATHENA_PROMPT_METADATA.useWhen?.some((entry) => - entry.includes("tradeoffs"), - ) - expect(hasTradeoffs).toBe(true) - }) - }) - - describe("#when checking avoidWhen entries", () => { - it("#then includes an entry about implementation tasks", () => { - const hasImplWarning = ATHENA_PROMPT_METADATA.avoidWhen?.some((entry) => - entry.includes("Implementation tasks"), - ) - expect(hasImplWarning).toBe(true) - }) - - it("#then includes an entry about subtask misuse", () => { - const hasSubtaskWarning = ATHENA_PROMPT_METADATA.avoidWhen?.some((entry) => - entry.includes("Subtasks"), - ) - expect(hasSubtaskWarning).toBe(true) - }) - }) - - describe("#when checking metadata shape", () => { - it("#then has category advisor", () => { - expect(ATHENA_PROMPT_METADATA.category).toBe("advisor") - }) - - it("#then has cost EXPENSIVE", () => { - expect(ATHENA_PROMPT_METADATA.cost).toBe("EXPENSIVE") - }) - - it("#then has promptAlias Athena", () => { - expect(ATHENA_PROMPT_METADATA.promptAlias).toBe("Athena") - }) - }) - }) -}) describe("Non-interactive prompt config injection placeholders", () => { describe("#given the non-interactive prompt", () => { diff --git a/src/agents/athena/index.ts b/src/agents/athena/index.ts index 1bc1dfca8..d42060be7 100644 --- a/src/agents/athena/index.ts +++ b/src/agents/athena/index.ts @@ -1,4 +1,4 @@ -export { createAthenaAgent, ATHENA_PROMPT_METADATA } from "./agent" +export { createAthenaAgent } from "./agent" export { createAthenaJuniorAgent, ATHENA_JUNIOR_PROMPT_METADATA } from "./athena-junior-agent" export { createCouncilMemberAgent, COUNCIL_MEMBER_PROMPT, COUNCIL_SOLO_ADDENDUM, COUNCIL_DELEGATION_ADDENDUM } from "./council-member-agent" export { COUNCIL_INTENT_ADDENDUMS } from "./council-intent-addendums" diff --git a/src/tools/switch-agent/tools.test.ts b/src/tools/switch-agent/tools.test.ts index 534551d18..475d858ea 100644 --- a/src/tools/switch-agent/tools.test.ts +++ b/src/tools/switch-agent/tools.test.ts @@ -188,21 +188,19 @@ describe("switch_agent tool", () => { expect(promptedSessions[0]!.path.id).toBe("direct-id-123") }) - //#given valid athena switch args + //#given athena switch args (athena is not a valid switch target) //#when execute is called - //#then it creates a new session and prompts with the athena agent - test("should create session and prompt for athena switch", async () => { + //#then it rejects the switch since athena primary is not in ALLOWED_AGENTS + test("should reject athena as switch target", async () => { const tool = createToolWithMockClient() const result = await tool.execute( { agent: "athena", context: "Run council analysis on the architecture decision" }, toolContext ) + expect(result).toContain("Invalid switch target") expect(result).toContain("athena") - expect(result).toContain("new-session-abc") - expect(createdSessions).toHaveLength(1) - expect(promptedSessions).toHaveLength(1) - expect(promptedSessions[0]!.path.id).toBe("new-session-abc") - expect(promptedSessions[0]!.body.parts[0]!.text).toBe("Run council analysis on the architecture decision") + expect(createdSessions).toHaveLength(0) + expect(promptedSessions).toHaveLength(0) }) }) diff --git a/src/tools/switch-agent/tools.ts b/src/tools/switch-agent/tools.ts index f4630d714..d143bba15 100644 --- a/src/tools/switch-agent/tools.ts +++ b/src/tools/switch-agent/tools.ts @@ -8,9 +8,9 @@ const DESCRIPTION = "with the provided context as its starting prompt. Use this to route work to another agent " + "(e.g., Atlas for fixes, Prometheus for planning). The switch executes when the current agent's turn completes.\n\n" + "Permanent one-way handoff. Use ONLY when you're the wrong agent for the overall job, NEVER for subtasks (use task()). " + - "Targets: atlas, prometheus, sisyphus, hephaestus, athena (multi-model council)." + "Targets: atlas, prometheus, sisyphus, hephaestus." -const ALLOWED_AGENTS = new Set(["atlas", "prometheus", "sisyphus", "hephaestus", "athena"]) +const ALLOWED_AGENTS = new Set(["atlas", "prometheus", "sisyphus", "hephaestus"]) type SessionClient = { session: {