History

Use tools.search as the sole sandbox tool search API

Rhys Sullivan committed 7 months ago

Commit 05d78bc1 parent 4ac9df03 files · +24 −25Browse files

Unified · Split

3 files
  1. packages/core/execution/src/description.ts +6 −6
  2. packages/core/execution/src/index.ts +1 −2
  3. packages/core/execution/src/tool-invoker.test.ts +17 −17
packages/core/execution/src/description.ts+6−6
@@ -30,20 +30,20 @@ const formatDescription = ( · 29 unmodified lines
3030 "",
3131 "## Workflow",
3232 "",
33− '1. `const matches = await tools.discover({ query: "<intent + key nouns>", limit: 12 });`',
33+ '1. `const matches = await tools.search({ query: "<intent + key nouns>", limit: 12 });`',
3434 '2. `const path = matches[0]?.path; if (!path) return "No matching tools found.";`',
3535 "3. `const details = await tools.describe.tool({ path });`",
3636 "4. Use `details.inputTypeScript` / `details.outputTypeScript` and `details.typeScriptDefinitions` for compact shapes.",
37− "5. Use `tools.executor.tools.search(...)` when you want ranked tool search explicitly, and `tools.executor.sources.list()` when you need configured source inventory.",
37+ "5. Use `tools.executor.sources.list()` when you need configured source inventory.",
3838 "6. Call the tool: `const result = await tools.<path>(input);`",
3939 "",
4040 "## Rules",
4141 "",
42− "- `tools.discover()` and `tools.executor.tools.search()` return ranked matches, best-first. Use short intent phrases like `github issues`, `repo details`, or `create calendar event`.",
43− "- When you already know the namespace, narrow with `tools.discover({ namespace: \"github\", query: \"issues\" })` or `tools.executor.tools.search({ namespace: \"github\", query: \"issues\" })`.",
42+ "- `tools.search()` returns ranked matches, best-first. Use short intent phrases like `github issues`, `repo details`, or `create calendar event`.",
43+ "- When you already know the namespace, narrow with `tools.search({ namespace: \"github\", query: \"issues\" })`.",
4444 "- Use `tools.executor.sources.list()` to inspect configured sources and their tool counts.",
45− "- The `tools` object is a lazy proxy — `Object.keys(tools)` won't work. Use the discovery helpers instead.",
46− "- Pass an object to system tools, e.g. `tools.discover({ query: \"...\" })`, `tools.executor.tools.search({ query: \"...\" })`, `tools.executor.sources.list()`, and `tools.describe.tool({ path })`.",
45+ "- The `tools` object is a lazy proxy — `Object.keys(tools)` won't work. Use `tools.search()` or `tools.executor.sources.list()` instead.",
46+ "- Pass an object to system tools, e.g. `tools.search({ query: \"...\" })`, `tools.executor.sources.list()`, and `tools.describe.tool({ path })`.",
4747 "- `tools.describe.tool()` returns compact TypeScript shapes. Use `inputTypeScript`, `outputTypeScript`, and `typeScriptDefinitions`.",
4848 "- Do not use `fetch` — all API calls go through `tools.*`.",
4949 "- If execution pauses for interaction, resume it with the returned `resumePayload`.",
packages/core/execution/src/index.ts+1−2
@@ -13,8 +13,7 @@ export { buildExecuteDescription } from "./description"; · 12 unmodified lines
1313 export { ExecutionToolError } from "./errors";
1414 export {
1515 makeExecutorToolInvoker,
16− discoverTools,
17− searchExecutorTools,
16+ searchTools,
1817 listExecutorSources,
1918 describeTool,
2019 } from "./tool-invoker";
packages/core/execution/src/tool-invoker.test.ts+17−17
@@ -10,7 +10,7 @@ import { · 9 unmodified lines
1010 tool,
1111 } from "@executor/sdk";
1212 import { createExecutionEngine } from "./engine";
13−import { describeTool, discoverTools } from "./tool-invoker";
13+import { describeTool, searchTools } from "./tool-invoker";
1414
1515 const EmptyInput = Schema.Struct({});
1616 const RepoInput = Schema.Struct({
@@ -95,16 +95,16 @@ describe("tool discovery", () => { · 78 unmodified lines
9595 Effect.gen(function* () {
9696 const executor = yield* makeSearchExecutor();
9797
98− const githubMatches = yield* discoverTools(executor, "github issues", 5);
98+ const githubMatches = yield* searchTools(executor, "github issues", 5);
9999 expect(githubMatches.map((match) => match.path)).toEqual([
100100 "github.listRepositoryIssues",
101101 ]);
102102 expect(githubMatches[0]?.score ?? 0).toBeGreaterThan(0);
103103
104− const repoMatches = yield* discoverTools(executor, "repo details", 5);
104+ const repoMatches = yield* searchTools(executor, "repo details", 5);
105105 expect(repoMatches[0]?.path).toBe("github.getRepositoryDetails");
106106
107− const crmMatches = yield* discoverTools(executor, "crm create contact", 5);
107+ const crmMatches = yield* searchTools(executor, "crm create contact", 5);
108108 expect(crmMatches[0]?.path).toBe("crm.createContact");
109109 expect(crmMatches[0]?.score ?? 0).toBeGreaterThan(crmMatches[1]?.score ?? 0);
110110 }),
@@ -113,7 +113,7 @@ describe("tool discovery", () => { · 2 unmodified lines
113113 it.effect("returns no matches for empty queries instead of listing arbitrary tools", () =>
114114 Effect.gen(function* () {
115115 const executor = yield* makeSearchExecutor();
116− const matches = yield* discoverTools(executor, "", 5);
116+ const matches = yield* searchTools(executor, "", 5);
117117 expect(matches).toEqual([]);
118118 }),
119119 );
@@ -122,14 +122,14 @@ describe("tool discovery", () => { · 2 unmodified lines
122122 Effect.gen(function* () {
123123 const executor = yield* makeSearchExecutor();
124124
125− const githubOnly = yield* discoverTools(executor, "list", 5, {
125+ const githubOnly = yield* searchTools(executor, "list", 5, {
126126 namespace: "github",
127127 });
128128 expect(githubOnly.map((match) => match.path)).toEqual([
129129 "github.listRepositoryIssues",
130130 ]);
131131
132− const crmOnly = yield* discoverTools(executor, "list", 5, {
132+ const crmOnly = yield* searchTools(executor, "list", 5, {
133133 namespace: "crm",
134134 });
135135 expect(crmOnly.map((match) => match.path)).toEqual([
@@ -138,7 +138,7 @@ describe("tool discovery", () => { · 2 unmodified lines
138138
139139 const sandboxResult = yield* Effect.promise(() =>
140140 createExecutionEngine({ executor }).execute(
141− 'return await tools.discover({ namespace: "crm", query: "create contact", limit: 5 });',
141+ 'return await tools.search({ namespace: "crm", query: "create contact", limit: 5 });',
142142 { onElicitation: acceptAll },
143143 ),
144144 );
@@ -169,7 +169,7 @@ describe("tool discovery", () => { · 24 unmodified lines
169169
170170 const searched = yield* Effect.promise(() =>
171171 createExecutionEngine({ executor }).execute(
172− 'return await tools.executor.tools.search({ query: "list contacts", namespace: "crm", limit: 5 });',
172+ 'return await tools.search({ query: "list contacts", namespace: "crm", limit: 5 });',
173173 { onElicitation: acceptAll },
174174 ),
175175 );
@@ -219,7 +219,7 @@ describe("tool discovery", () => { · 43 unmodified lines
219219 engine.execute(
220220 [
221221 "try {",
222− " await tools.discover(\"github issues\");",
222+ " await tools.search(\"github issues\");",
223223 " return \"unexpected\";",
224224 "} catch (error) {",
225225 " return error instanceof Error ? error.message : String(error);",
@@ -230,12 +230,12 @@ describe("tool discovery", () => { · 4 unmodified lines
230230 );
231231 expect(invalid.error).toBeUndefined();
232232 expect(String(invalid.result)).toContain(
233− "tools.discover expects an object: { query?: string; namespace?: string; limit?: number }",
233+ "tools.search expects an object: { query?: string; namespace?: string; limit?: number }",
234234 );
235235
236236 const emptyQuery = yield* Effect.promise(() =>
237237 engine.execute(
238− "return await tools.discover({ query: \"\", limit: 5 });",
238+ "return await tools.search({ query: \"\", limit: 5 });",
239239 { onElicitation: acceptAll },
240240 ),
241241 );
@@ -260,15 +260,15 @@ describe("tool discovery", () => { · 18 unmodified lines
260260 "tools.describe.tool no longer accepts includeSchemas",
261261 );
262262
263− const invalidExecutorSearch = yield* Effect.promise(() =>
263+ const invalidSearch = yield* Effect.promise(() =>
264264 engine.execute(
265− 'try { return await tools.executor.tools.search("crm"); } catch (error) { return error instanceof Error ? error.message : String(error); }',
265+ 'try { return await tools.search("crm"); } catch (error) { return error instanceof Error ? error.message : String(error); }',
266266 { onElicitation: acceptAll },
267267 ),
268268 );
269− expect(invalidExecutorSearch.error).toBeUndefined();
270− expect(String(invalidExecutorSearch.result)).toContain(
271− "tools.executor.tools.search expects an object",
269+ expect(invalidSearch.error).toBeUndefined();
270+ expect(String(invalidSearch.result)).toContain(
271+ "tools.search expects an object",
272272 );
273273 }),
274274 );