diff --git a/packages/server/src/server/agent/providers/pi/extensions/tintinweb-pi-subagents/index.test.ts b/packages/server/src/server/agent/providers/pi/extensions/tintinweb-pi-subagents/index.test.ts index b015b0f4f5..e083403d81 100644 --- a/packages/server/src/server/agent/providers/pi/extensions/tintinweb-pi-subagents/index.test.ts +++ b/packages/server/src/server/agent/providers/pi/extensions/tintinweb-pi-subagents/index.test.ts @@ -1,7 +1,10 @@ import { describe, expect, test } from "vitest"; import { fileURLToPath } from "node:url"; import { createPiExtensionHost } from "../index.js"; -import { readSubagentFixture, verifySubagentFixture } from "../subagent-fixture-test.js"; +import { + readSubagentFixture, + verifySubagentFixture, +} from "../subagent-fixture-test.js"; describe("@tintinweb/pi-subagents adapter", () => { test("exposes the background output file while the child is running", () => { @@ -13,71 +16,105 @@ describe("@tintinweb/pi-subagents adapter", () => { result: { details: { agentId: "native-1", status: "background" }, content: [ - { type: "text", text: "Agent started in background.\nOutput file: /tmp/child.output\n" }, + { + type: "text", + text: "Agent started in background.\nOutput file: /tmp/child.output\n", + }, ], }, }); expect(mapping?.subagents).toEqual([ expect.objectContaining({ id: "call-1", status: "running" }), ]); - expect(mapping?.childSessions).toEqual([{ id: "call-1", file: "/tmp/child.output" }]); + expect(mapping?.childSessions).toEqual([ + { id: "call-1", file: "/tmp/child.output" }, + ]); }); test("maps captured foreground lifecycle live and on replay", async () => { const events = await verifySubagentFixture( - readSubagentFixture(new URL("./fixtures/foreground.json", import.meta.url)), + readSubagentFixture( + new URL("./fixtures/foreground.json", import.meta.url) + ) ); expect( events .filter((event) => event.event.type === "upsert") - .map((event) => (event.event.type === "upsert" ? event.event.status : null)), + .map((event) => + event.event.type === "upsert" ? event.event.status : null + ) ).toEqual(["running", "completed"]); }); // #5828: the extension writes a transcript for foreground agents too, but its // foreground result carries no `Output file:` line, so the child opens empty. test("exposes the foreground child's transcript when it completes", () => { - const fixture = readSubagentFixture(new URL("./fixtures/foreground.json", import.meta.url)); - const end = fixture.events.find((event) => event.type === "tool_execution_end") as { + const fixture = readSubagentFixture( + new URL("./fixtures/foreground.json", import.meta.url) + ); + const end = fixture.events.find( + (event) => event.type === "tool_execution_end" + ) as { toolCallId: string; - result: Parameters["mapToolCall"]>[0]["result"]; + result: Parameters< + ReturnType["mapToolCall"] + >[0]["result"]; }; const mapping = createPiExtensionHost().mapToolCall({ callId: end.toolCallId, toolName: "Agent", - args: { subagent_type: "general-purpose", prompt: "list the files in this empty workspace" }, + args: { + subagent_type: "general-purpose", + prompt: "list the files in this empty workspace", + }, status: "completed", result: end.result, }); expect(mapping?.subagents).toEqual([ expect.objectContaining({ id: end.toolCallId, status: "completed" }), ]); - expect(mapping?.childSessions).toEqual([{ id: end.toolCallId, file: expect.any(String) }]); + expect(mapping?.childSessions).toEqual([ + { id: end.toolCallId, file: expect.any(String) }, + ]); }); test("uses a structured notification to complete a background child", async () => { - const source = readSubagentFixture(new URL("./fixtures/background.json", import.meta.url)); + const source = readSubagentFixture( + new URL("./fixtures/background.json", import.meta.url) + ); const file = ( source.messages.find((message) => message.role === "custom") as { details: { outputFile: string }; } ).details.outputFile; - const fixture = readSubagentFixture(new URL("./fixtures/background.json", import.meta.url), { - from: file, - to: fileURLToPath(new URL("./fixtures/child-session.jsonl", import.meta.url)), - }); + const fixture = readSubagentFixture( + new URL("./fixtures/background.json", import.meta.url), + { + from: file, + to: fileURLToPath( + new URL("./fixtures/child-session.jsonl", import.meta.url) + ), + } + ); const events = await verifySubagentFixture(fixture); expect( events .filter((event) => event.event.type === "upsert") - .map((event) => (event.event.type === "upsert" ? event.event.status : null)), + .map((event) => + event.event.type === "upsert" ? event.event.status : null + ) ).toEqual(["running", "running", "completed"]); - expect(events.filter((event) => event.event.type === "timeline").length).toBeGreaterThan(0); + expect( + events.filter((event) => event.event.type === "timeline").length + ).toBeGreaterThan(0); }); test("completes every background child in a grouped notification", async () => { const events = await verifySubagentFixture( - readSubagentFixture(new URL("./fixtures/background-group.json", import.meta.url)), + readSubagentFixture( + new URL("./fixtures/background-group.json", import.meta.url) + ) ); const finalStatus = new Map(); for (const { event } of events) { - if (event.type === "upsert" && event.status) finalStatus.set(event.id, event.status); + if (event.type === "upsert" && event.status) + finalStatus.set(event.id, event.status); } expect(Object.fromEntries(finalStatus)).toEqual({ call_277173: "completed", @@ -93,7 +130,7 @@ describe("@tintinweb/pi-subagents adapter", () => { args: { prompt: "foo" }, status: "completed", result: { details: { agentId: "other", status: "completed" } }, - }), + }) ).toBeUndefined(); }); });