diff --git a/nodejs/test/e2e/tools.e2e.test.ts b/nodejs/test/e2e/tools.e2e.test.ts index 29e2ccf21..c505f8aa8 100644 --- a/nodejs/test/e2e/tools.e2e.test.ts +++ b/nodejs/test/e2e/tools.e2e.test.ts @@ -6,7 +6,7 @@ import { writeFile } from "fs/promises"; import { join } from "path"; import { assert, describe, expect, it } from "vitest"; import { z } from "zod"; -import { defineTool, approveAll } from "../../src/index.js"; +import { defineTool, approveAll, ToolSet } from "../../src/index.js"; import type { PermissionRequest } from "../../src/index.js"; import { createSdkTestContext } from "./harness/sdkTestContext"; @@ -45,6 +45,54 @@ describe("Custom tools", async () => { expect(assistantMessage?.data.content).toContain("HELLO"); }); + it("low_level_tool_definition", async () => { + let currentPhase = ""; + const session = await client.createSession({ + onPermissionRequest: approveAll, + availableTools: new ToolSet().addCustom("*").addBuiltIn("web_fetch"), + tools: [ + defineTool("set_current_phase", { + description: "Sets the current phase of the agent", + parameters: z.object({ + phase: z.enum(["searching", "analyzing", "done"]), + }), + handler: ({ phase }) => { + currentPhase = phase; + return `Phase set to ${phase}`; + }, + }), + defineTool("search_items", { + description: "Search for items by keyword", + parameters: z.object({ + keyword: z.string(), + }), + handler: (_args, invocation) => { + const args = invocation.arguments as Record; + if (args.keyword !== "copilot") { + throw new Error( + `Expected keyword to be 'copilot', got: ${String(args.keyword)}` + ); + } + return "Found: item_alpha, item_beta"; + }, + }), + ], + }); + + const assistantMessage = await session.sendAndWait({ + prompt: "First, set the current phase to 'analyzing'. Then search for items with keyword 'copilot'. Report the phase and search results.", + }); + + const content = assistantMessage?.data.content ?? ""; + expect(content.length).toBeGreaterThan(0); + expect(content.toLowerCase()).toContain("analyzing"); + expect( + content.toLowerCase().includes("item_alpha") || + content.toLowerCase().includes("item_beta") + ).toBe(true); + expect(currentPhase).toBe("analyzing"); + }); + it("handles tool calling errors", async () => { const session = await client.createSession({ onPermissionRequest: approveAll,