@geminixiang/mikan 1.0.0-beta.73 → 1.0.0-beta.75
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +21 -0
- package/dist/adapters/slack/bot.d.ts.map +1 -1
- package/dist/adapters/slack/bot.js +1 -3
- package/dist/adapters/slack/bot.js.map +1 -1
- package/dist/adapters/slack/task-intent.d.ts.map +1 -1
- package/dist/adapters/slack/task-intent.js +1 -1
- package/dist/adapters/slack/task-intent.js.map +1 -1
- package/dist/adapters/slack/tools/blockkit.d.ts +1 -0
- package/dist/adapters/slack/tools/blockkit.d.ts.map +1 -1
- package/dist/adapters/slack/tools/blockkit.js +1 -0
- package/dist/adapters/slack/tools/blockkit.js.map +1 -1
- package/dist/adapters/web/admin/portal.js +33 -17
- package/dist/adapters/web/admin/portal.js.map +1 -1
- package/dist/adapters/web/portal-shell.js +5 -2
- package/dist/adapters/web/portal-shell.js.map +1 -1
- package/dist/harness/execution-env.js +34 -1
- package/dist/harness/execution-env.js.map +1 -1
- package/dist/harness/jev.d.ts +10 -1
- package/dist/harness/jev.d.ts.map +1 -1
- package/dist/harness/jev.js +17 -1
- package/dist/harness/jev.js.map +1 -1
- package/dist/harness/presenter.d.ts.map +1 -1
- package/dist/harness/presenter.js +8 -3
- package/dist/harness/presenter.js.map +1 -1
- package/dist/harness/prompt.js +1 -1
- package/dist/harness/prompt.js.map +1 -1
- package/dist/harness/tools/generate-image.d.ts +1 -0
- package/dist/harness/tools/generate-image.d.ts.map +1 -1
- package/dist/harness/tools/generate-image.js +1 -0
- package/dist/harness/tools/generate-image.js.map +1 -1
- package/dist/harness/tools/host-fn-tool.d.ts +10 -1
- package/dist/harness/tools/host-fn-tool.d.ts.map +1 -1
- package/dist/harness/tools/host-fn-tool.js +22 -2
- package/dist/harness/tools/host-fn-tool.js.map +1 -1
- package/dist/harness/tools/index.d.ts.map +1 -1
- package/dist/harness/tools/index.js +12 -1
- package/dist/harness/tools/index.js.map +1 -1
- package/dist/harness/tools/jev-browser.d.ts +130 -0
- package/dist/harness/tools/jev-browser.d.ts.map +1 -0
- package/dist/harness/tools/jev-browser.js +434 -0
- package/dist/harness/tools/jev-browser.js.map +1 -0
- package/dist/harness/tools/jev.d.ts.map +1 -1
- package/dist/harness/tools/jev.js +1 -0
- package/dist/harness/tools/jev.js.map +1 -1
- package/dist/harness/tools/sandbox.d.ts +1 -0
- package/dist/harness/tools/sandbox.d.ts.map +1 -1
- package/dist/harness/tools/sandbox.js +1 -0
- package/dist/harness/tools/sandbox.js.map +1 -1
- package/dist/harness/tools/secret-redaction.d.ts +34 -0
- package/dist/harness/tools/secret-redaction.d.ts.map +1 -0
- package/dist/harness/tools/secret-redaction.js +77 -0
- package/dist/harness/tools/secret-redaction.js.map +1 -0
- package/dist/observability/index.d.ts +11 -2
- package/dist/observability/index.d.ts.map +1 -1
- package/dist/observability/index.js +30 -0
- package/dist/observability/index.js.map +1 -1
- package/dist/observability/sentry.d.ts +9 -2
- package/dist/observability/sentry.d.ts.map +1 -1
- package/dist/observability/sentry.js +28 -0
- package/dist/observability/sentry.js.map +1 -1
- package/dist/observability/types.d.ts +15 -0
- package/dist/observability/types.d.ts.map +1 -1
- package/dist/observability/types.js.map +1 -1
- package/dist/runtime/conversation-runtime.d.ts.map +1 -1
- package/dist/runtime/conversation-runtime.js +19 -10
- package/dist/runtime/conversation-runtime.js.map +1 -1
- package/dist/types.d.ts +8 -0
- package/dist/types.d.ts.map +1 -1
- package/dist/types.js.map +1 -1
- package/package.json +4 -3
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"generate-image.js","sourceRoot":"","sources":["../../../src/harness/tools/generate-image.ts"],"names":[],"mappings":"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","sourcesContent":["import type { AgentTool } from \"@earendil-works/pi-agent-core\";\nimport type { Api, Model } from \"@earendil-works/pi-ai\";\nimport { Type } from \"@sinclair/typebox\";\nimport { writeFile } from \"node:fs/promises\";\nimport { join } from \"node:path\";\nimport { randomUUID } from \"node:crypto\";\n\nconst schema = Type.Object({\n prompt: Type.String({ description: \"Description of the image to generate\" }),\n size: Type.Optional(Type.String({ description: \"Requested image size, for example 1024x1024\" })),\n quality: Type.Optional(\n Type.String({ description: \"Requested image quality, for example low, medium, or high\" }),\n ),\n});\n\ninterface ImageResponse {\n data?: Array<{ b64_json?: string }>;\n error?: { message?: string };\n}\n\nexport function createGenerateImageTool(options: {\n model: Model<Api>;\n getApiKey: () => Promise<string | undefined>;\n /** Host directory the generated image is written into. Must be the\n * conversation's own office dir so the agent can also reach the file\n * from inside the sandbox; the workspace base is NOT guest-visible. */\n outputDir: string;\n}): {\n tool: AgentTool<typeof schema>;\n /** The callback receives the HOST path of the generated file. The image is\n * written host-side, so upload must not stage it through the sandbox the\n * way the attach tool does — the file may not be mounted there. */\n setUploadFunction: (fn: (hostPath: string, title?: string) => Promise<void>) => void;\n} {\n let uploadFn: ((hostPath: string, title?: string) => Promise<void>) | null = null;\n\n return {\n tool: {\n name: \"generate_image\",\n label: \"generate image\",\n description:\n \"Generate an image with the configured model provider and attach it to the response.\",\n parameters: schema,\n execute: async (_toolCallId, params, signal) => {\n if (!uploadFn) throw new Error(\"Upload function not configured\");\n if (!options.model.baseUrl)\n throw new Error(\"Image generation requires a configured model baseUrl\");\n const apiKey = await options.getApiKey();\n if (!apiKey) throw new Error(`No API key configured for ${options.model.provider}`);\n\n const response = await fetch(\n `${options.model.baseUrl.replace(/\\/$/, \"\")}/images/generations`,\n {\n method: \"POST\",\n signal,\n headers: {\n ...options.model.headers,\n Authorization: `Bearer ${apiKey}`,\n \"Content-Type\": \"application/json\",\n },\n body: JSON.stringify({\n model: options.model.id,\n prompt: params.prompt,\n ...(params.size ? { size: params.size } : {}),\n ...(params.quality ? { quality: params.quality } : {}),\n response_format: \"b64_json\",\n }),\n },\n );\n const body = (await response.json()) as ImageResponse;\n if (!response.ok) {\n throw new Error(\n `Image generation with model \"${options.model.id}\" failed: ` +\n (body.error?.message ?? `HTTP ${response.status}`),\n );\n }\n const encoded = body.data?.[0]?.b64_json;\n if (!encoded) throw new Error(\"Image generation response contained no image\");\n\n const fileName = `generated-${randomUUID()}.png`;\n const filePath = join(options.outputDir, fileName);\n await writeFile(filePath, Buffer.from(encoded, \"base64\"));\n await uploadFn(filePath, fileName);\n\n return {\n content: [{ type: \"text\" as const, text: `Generated and attached image: ${fileName}` }],\n details: { fileName },\n };\n },\n },\n setUploadFunction: (fn) => {\n uploadFn = fn;\n },\n };\n}\n"]}
|
|
1
|
+
{"version":3,"file":"generate-image.js","sourceRoot":"","sources":["../../../src/harness/tools/generate-image.ts"],"names":[],"mappings":"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","sourcesContent":["import type { AgentTool } from \"@earendil-works/pi-agent-core\";\nimport type { Api, Model } from \"@earendil-works/pi-ai\";\nimport { Type } from \"@sinclair/typebox\";\nimport { writeFile } from \"node:fs/promises\";\nimport { join } from \"node:path\";\nimport { randomUUID } from \"node:crypto\";\n\nconst schema = Type.Object({\n label: Type.String({ description: \"Brief description of this action (shown to user)\" }),\n prompt: Type.String({ description: \"Description of the image to generate\" }),\n size: Type.Optional(Type.String({ description: \"Requested image size, for example 1024x1024\" })),\n quality: Type.Optional(\n Type.String({ description: \"Requested image quality, for example low, medium, or high\" }),\n ),\n});\n\ninterface ImageResponse {\n data?: Array<{ b64_json?: string }>;\n error?: { message?: string };\n}\n\nexport function createGenerateImageTool(options: {\n model: Model<Api>;\n getApiKey: () => Promise<string | undefined>;\n /** Host directory the generated image is written into. Must be the\n * conversation's own office dir so the agent can also reach the file\n * from inside the sandbox; the workspace base is NOT guest-visible. */\n outputDir: string;\n}): {\n tool: AgentTool<typeof schema>;\n /** The callback receives the HOST path of the generated file. The image is\n * written host-side, so upload must not stage it through the sandbox the\n * way the attach tool does — the file may not be mounted there. */\n setUploadFunction: (fn: (hostPath: string, title?: string) => Promise<void>) => void;\n} {\n let uploadFn: ((hostPath: string, title?: string) => Promise<void>) | null = null;\n\n return {\n tool: {\n name: \"generate_image\",\n label: \"generate image\",\n description:\n \"Generate an image with the configured model provider and attach it to the response.\",\n parameters: schema,\n execute: async (_toolCallId, params, signal) => {\n if (!uploadFn) throw new Error(\"Upload function not configured\");\n if (!options.model.baseUrl)\n throw new Error(\"Image generation requires a configured model baseUrl\");\n const apiKey = await options.getApiKey();\n if (!apiKey) throw new Error(`No API key configured for ${options.model.provider}`);\n\n const response = await fetch(\n `${options.model.baseUrl.replace(/\\/$/, \"\")}/images/generations`,\n {\n method: \"POST\",\n signal,\n headers: {\n ...options.model.headers,\n Authorization: `Bearer ${apiKey}`,\n \"Content-Type\": \"application/json\",\n },\n body: JSON.stringify({\n model: options.model.id,\n prompt: params.prompt,\n ...(params.size ? { size: params.size } : {}),\n ...(params.quality ? { quality: params.quality } : {}),\n response_format: \"b64_json\",\n }),\n },\n );\n const body = (await response.json()) as ImageResponse;\n if (!response.ok) {\n throw new Error(\n `Image generation with model \"${options.model.id}\" failed: ` +\n (body.error?.message ?? `HTTP ${response.status}`),\n );\n }\n const encoded = body.data?.[0]?.b64_json;\n if (!encoded) throw new Error(\"Image generation response contained no image\");\n\n const fileName = `generated-${randomUUID()}.png`;\n const filePath = join(options.outputDir, fileName);\n await writeFile(filePath, Buffer.from(encoded, \"base64\"));\n await uploadFn(filePath, fileName);\n\n return {\n content: [{ type: \"text\" as const, text: `Generated and attached image: ${fileName}` }],\n details: { fileName },\n };\n },\n },\n setUploadFunction: (fn) => {\n uploadFn = fn;\n },\n };\n}\n"]}
|
|
@@ -1,11 +1,20 @@
|
|
|
1
1
|
import type { AgentTool } from "@earendil-works/pi-agent-core";
|
|
2
|
-
import type
|
|
2
|
+
import { type Static, type TSchema } from "@sinclair/typebox";
|
|
3
3
|
/**
|
|
4
4
|
* A host-backed tool whose implementation is injected per run: a pack's
|
|
5
5
|
* bindRun binds the function for the current conversation (or null to
|
|
6
6
|
* disable the tool). Owns the choreography every such tool used to repeat
|
|
7
7
|
* by hand — the holder + setter pair, the disabled-tool error, and the
|
|
8
8
|
* abort guard — so a tool module only states its schema and its run body.
|
|
9
|
+
*
|
|
10
|
+
* Every mikan-authored tool must carry a required `label` parameter (see
|
|
11
|
+
* `AGENTS.md`, "every model-facing tool schema must declare a required
|
|
12
|
+
* `label`"): the system prompt promises the model this contract
|
|
13
|
+
* unconditionally, and `harness/presenter.ts` renders it as the run's
|
|
14
|
+
* current step. Adding it here, once, for every `defineHostFnTool` caller
|
|
15
|
+
* is how that promise stays true without each tool module remembering to
|
|
16
|
+
* restate it — react.ts and all six `github_*` tools previously did not,
|
|
17
|
+
* so their progress lines rendered only the bare tool name.
|
|
9
18
|
*/
|
|
10
19
|
export declare function defineHostFnTool<TFn, TParams extends TSchema>(definition: {
|
|
11
20
|
name: string;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"host-fn-tool.d.ts","sourceRoot":"","sources":["../../../src/harness/tools/host-fn-tool.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,+BAA+B,CAAC;AAC/D,OAAO,KAAK,
|
|
1
|
+
{"version":3,"file":"host-fn-tool.d.ts","sourceRoot":"","sources":["../../../src/harness/tools/host-fn-tool.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,+BAA+B,CAAC;AAC/D,OAAO,EAAQ,KAAK,MAAM,EAAE,KAAK,OAAO,EAAE,MAAM,mBAAmB,CAAC;AAEpE;;;;;;;;;;;;;;;GAeG;AACH,wBAAgB,gBAAgB,CAAC,GAAG,EAAE,OAAO,SAAS,OAAO,EAAE,UAAU,EAAE;IACzE,IAAI,EAAE,MAAM,CAAC;IACb,WAAW,EAAE,MAAM,CAAC;IACpB,UAAU,EAAE,OAAO,CAAC;IACpB,wEAAwE;IACxE,WAAW,EAAE,MAAM,CAAC;IACpB,GAAG,EAAE,CACH,EAAE,EAAE,GAAG,EACP,IAAI,EAAE,MAAM,CAAC,OAAO,CAAC,EACrB,MAAM,CAAC,EAAE,WAAW,KACjB,UAAU,CAAC,SAAS,CAAC,OAAO,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC;CAChD,GAAG;IAAE,IAAI,EAAE,SAAS,CAAC,OAAO,CAAC,CAAC;IAAC,KAAK,EAAE,CAAC,EAAE,EAAE,GAAG,GAAG,IAAI,KAAK,IAAI,CAAA;CAAE,CAmChE"}
|
|
@@ -1,17 +1,36 @@
|
|
|
1
|
+
import { Type } from "@sinclair/typebox";
|
|
1
2
|
/**
|
|
2
3
|
* A host-backed tool whose implementation is injected per run: a pack's
|
|
3
4
|
* bindRun binds the function for the current conversation (or null to
|
|
4
5
|
* disable the tool). Owns the choreography every such tool used to repeat
|
|
5
6
|
* by hand — the holder + setter pair, the disabled-tool error, and the
|
|
6
7
|
* abort guard — so a tool module only states its schema and its run body.
|
|
8
|
+
*
|
|
9
|
+
* Every mikan-authored tool must carry a required `label` parameter (see
|
|
10
|
+
* `AGENTS.md`, "every model-facing tool schema must declare a required
|
|
11
|
+
* `label`"): the system prompt promises the model this contract
|
|
12
|
+
* unconditionally, and `harness/presenter.ts` renders it as the run's
|
|
13
|
+
* current step. Adding it here, once, for every `defineHostFnTool` caller
|
|
14
|
+
* is how that promise stays true without each tool module remembering to
|
|
15
|
+
* restate it — react.ts and all six `github_*` tools previously did not,
|
|
16
|
+
* so their progress lines rendered only the bare tool name.
|
|
7
17
|
*/
|
|
8
18
|
export function defineHostFnTool(definition) {
|
|
9
19
|
let bound = null;
|
|
20
|
+
const schema = definition.parameters;
|
|
21
|
+
const parameters = {
|
|
22
|
+
...schema,
|
|
23
|
+
properties: {
|
|
24
|
+
label: Type.String({ description: "Brief description of this action (shown to user)" }),
|
|
25
|
+
...schema.properties,
|
|
26
|
+
},
|
|
27
|
+
required: ["label", ...(schema.required ?? [])],
|
|
28
|
+
};
|
|
10
29
|
const tool = {
|
|
11
30
|
name: definition.name,
|
|
12
31
|
label: definition.name,
|
|
13
32
|
description: definition.description,
|
|
14
|
-
parameters
|
|
33
|
+
parameters,
|
|
15
34
|
execute: async (_toolCallId, args, signal) => {
|
|
16
35
|
if (!bound) {
|
|
17
36
|
throw new Error(definition.unavailable);
|
|
@@ -19,7 +38,8 @@ export function defineHostFnTool(definition) {
|
|
|
19
38
|
if (signal?.aborted) {
|
|
20
39
|
throw new Error("Operation aborted");
|
|
21
40
|
}
|
|
22
|
-
|
|
41
|
+
const { label: _label, ...rest } = args;
|
|
42
|
+
return definition.run(bound, rest, signal);
|
|
23
43
|
},
|
|
24
44
|
};
|
|
25
45
|
return {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"host-fn-tool.js","sourceRoot":"","sources":["../../../src/harness/tools/host-fn-tool.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"host-fn-tool.js","sourceRoot":"","sources":["../../../src/harness/tools/host-fn-tool.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,IAAI,EAA6B,MAAM,mBAAmB,CAAC;AAEpE;;;;;;;;;;;;;;;GAeG;AACH,MAAM,UAAU,gBAAgB,CAA+B,UAW9D;IACC,IAAI,KAAK,GAAe,IAAI,CAAC;IAC7B,MAAM,MAAM,GAAG,UAAU,CAAC,UAAqB,CAAC;IAChD,MAAM,UAAU,GAAG;QACjB,GAAG,MAAM;QACT,UAAU,EAAE;YACV,KAAK,EAAE,IAAI,CAAC,MAAM,CAAC,EAAE,WAAW,EAAE,kDAAkD,EAAE,CAAC;YACvF,GAAG,MAAM,CAAC,UAAU;SACrB;QACD,QAAQ,EAAE,CAAC,OAAO,EAAE,GAAG,CAAE,MAAM,CAAC,QAAiC,IAAI,EAAE,CAAC,CAAC;KACpD,CAAC;IAExB,MAAM,IAAI,GAAuB;QAC/B,IAAI,EAAE,UAAU,CAAC,IAAI;QACrB,KAAK,EAAE,UAAU,CAAC,IAAI;QACtB,WAAW,EAAE,UAAU,CAAC,WAAW;QACnC,UAAU;QACV,OAAO,EAAE,KAAK,EAAE,WAAW,EAAE,IAAI,EAAE,MAAM,EAAE,EAAE;YAC3C,IAAI,CAAC,KAAK,EAAE,CAAC;gBACX,MAAM,IAAI,KAAK,CAAC,UAAU,CAAC,WAAW,CAAC,CAAC;YAC1C,CAAC;YACD,IAAI,MAAM,EAAE,OAAO,EAAE,CAAC;gBACpB,MAAM,IAAI,KAAK,CAAC,mBAAmB,CAAC,CAAC;YACvC,CAAC;YACD,MAAM,EAAE,KAAK,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,GAAG,IAA+B,CAAC;YACnE,OAAO,UAAU,CAAC,GAAG,CAAC,KAAK,EAAE,IAAuB,EAAE,MAAM,CAAC,CAAC;QAChE,CAAC;KACF,CAAC;IAEF,OAAO;QACL,IAAI;QACJ,KAAK,EAAE,CAAC,EAAE,EAAE,EAAE;YACZ,KAAK,GAAG,EAAE,CAAC;QACb,CAAC;KACF,CAAC;AACJ,CAAC","sourcesContent":["import type { AgentTool } from \"@earendil-works/pi-agent-core\";\nimport { Type, type Static, type TSchema } from \"@sinclair/typebox\";\n\n/**\n * A host-backed tool whose implementation is injected per run: a pack's\n * bindRun binds the function for the current conversation (or null to\n * disable the tool). Owns the choreography every such tool used to repeat\n * by hand — the holder + setter pair, the disabled-tool error, and the\n * abort guard — so a tool module only states its schema and its run body.\n *\n * Every mikan-authored tool must carry a required `label` parameter (see\n * `AGENTS.md`, \"every model-facing tool schema must declare a required\n * `label`\"): the system prompt promises the model this contract\n * unconditionally, and `harness/presenter.ts` renders it as the run's\n * current step. Adding it here, once, for every `defineHostFnTool` caller\n * is how that promise stays true without each tool module remembering to\n * restate it — react.ts and all six `github_*` tools previously did not,\n * so their progress lines rendered only the bare tool name.\n */\nexport function defineHostFnTool<TFn, TParams extends TSchema>(definition: {\n name: string;\n description: string;\n parameters: TParams;\n /** Error thrown when the tool executes with no bound implementation. */\n unavailable: string;\n run: (\n fn: TFn,\n args: Static<TParams>,\n signal?: AbortSignal,\n ) => ReturnType<AgentTool<TParams>[\"execute\"]>;\n}): { tool: AgentTool<TParams>; setFn: (fn: TFn | null) => void } {\n let bound: TFn | null = null;\n const schema = definition.parameters as TSchema;\n const parameters = {\n ...schema,\n properties: {\n label: Type.String({ description: \"Brief description of this action (shown to user)\" }),\n ...schema.properties,\n },\n required: [\"label\", ...((schema.required as string[] | undefined) ?? [])],\n } as unknown as TParams;\n\n const tool: AgentTool<TParams> = {\n name: definition.name,\n label: definition.name,\n description: definition.description,\n parameters,\n execute: async (_toolCallId, args, signal) => {\n if (!bound) {\n throw new Error(definition.unavailable);\n }\n if (signal?.aborted) {\n throw new Error(\"Operation aborted\");\n }\n const { label: _label, ...rest } = args as Record<string, unknown>;\n return definition.run(bound, rest as Static<TParams>, signal);\n },\n };\n\n return {\n tool,\n setFn: (fn) => {\n bound = fn;\n },\n };\n}\n"]}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/harness/tools/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,GAAG,EAAE,KAAK,EAAE,MAAM,uBAAuB,CAAC;AACxD,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,gBAAgB,CAAC;AAEvD,OAAO,KAAK,EAAE,QAAQ,EAAE,aAAa,EAAE,MAAM,wBAAwB,CAAC;AACtE,OAAO,KAAK,EAAE,aAAa,EAAE,yBAAyB,EAAE,MAAM,gBAAgB,CAAC;AAC/E,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,uBAAuB,CAAC;AAGxD,OAAO,EAAsC,KAAK,gBAAgB,EAAE,MAAM,eAAe,CAAC;
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/harness/tools/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,GAAG,EAAE,KAAK,EAAE,MAAM,uBAAuB,CAAC;AACxD,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,gBAAgB,CAAC;AAEvD,OAAO,KAAK,EAAE,QAAQ,EAAE,aAAa,EAAE,MAAM,wBAAwB,CAAC;AACtE,OAAO,KAAK,EAAE,aAAa,EAAE,yBAAyB,EAAE,MAAM,gBAAgB,CAAC;AAC/E,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,uBAAuB,CAAC;AAGxD,OAAO,EAAsC,KAAK,gBAAgB,EAAE,MAAM,eAAe,CAAC;AAE1F,OAAO,EAAE,eAAe,EAAE,MAAM,WAAW,CAAC;AAK5C,OAAO,KAAK,EAAE,uBAAuB,EAAE,sBAAsB,EAAE,MAAM,YAAY,CAAC;AAElF,OAAO,EAAE,kBAAkB,EAAE,MAAM,eAAe,CAAC;AAEnD,wBAAgB,gBAAgB,CAC9B,QAAQ,EAAE,QAAQ,EAClB,UAAU,EAAE,UAAU,EACtB,iBAAiB,CAAC,EAAE;IAClB,OAAO,EAAE,aAAa,CAAC;IACvB,kBAAkB,CAAC,EAAE,IAAI,CAAC,yBAAyB,EAAE,gBAAgB,GAAG,WAAW,CAAC,CAAC;CACtF;AACD;sEACsE;AACtE,yBAAyB,GAAE,SAAS,uBAAuB,EAAO,EAClE,eAAe,CAAC,EAAE;IAChB,KAAK,EAAE,KAAK,CAAC,GAAG,CAAC,CAAC;IAClB,SAAS,EAAE,MAAM,OAAO,CAAC,MAAM,GAAG,SAAS,CAAC,CAAC;IAC7C,SAAS,EAAE,MAAM,CAAC;CACnB,GACA;IACD,KAAK,EAAE,gBAAgB,EAAE,CAAC;IAC1B,iBAAiB,EAAE,CAAC,EAAE,EAAE,CAAC,QAAQ,EAAE,MAAM,EAAE,KAAK,CAAC,EAAE,MAAM,KAAK,OAAO,CAAC,IAAI,CAAC,KAAK,IAAI,CAAC;IACrF;;6EAEyE;IACzE,sBAAsB,EAAE,CAAC,EAAE,EAAE,CAAC,QAAQ,EAAE,MAAM,EAAE,KAAK,CAAC,EAAE,MAAM,KAAK,OAAO,CAAC,IAAI,CAAC,KAAK,IAAI,CAAC;IAC1F,SAAS,EAAE,UAAU,CAAC,OAAO,eAAe,CAAC,CAAC,WAAW,CAAC,CAAC;IAC3D,gBAAgB,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,KAAK,EAAE,MAAM,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC,GAAG,IAAI,KAAK,IAAI,CAAC;IAC1E,qBAAqB,EAAE,CAAC,GAAG,EAAE,sBAAsB,KAAK,IAAI,CAAC;IAC7D,eAAe,EAAE,CAAC,OAAO,EAAE;QACzB,QAAQ,EAAE,MAAM,CAAC;QACjB,cAAc,EAAE,MAAM,CAAC;QACvB,gBAAgB,EAAE,gBAAgB,CAAC;QACnC,MAAM,EAAE,MAAM,CAAC;KAChB,KAAK,IAAI,CAAC;IACX,iBAAiB,EAAE,CAAC,OAAO,EAAE;QAAE,OAAO,EAAE,aAAa,CAAC;QAAC,MAAM,EAAE,MAAM,CAAA;KAAE,KAAK,IAAI,CAAC;CAClF,CAiDA"}
|
|
@@ -2,8 +2,10 @@ import { createAttachTool } from "./attach.js";
|
|
|
2
2
|
import { createEventTool } from "./event.js";
|
|
3
3
|
import { createGenerateImageTool } from "./generate-image.js";
|
|
4
4
|
import { adaptAgentTool, createSandboxTools } from "./pi-tools.js";
|
|
5
|
+
import { withSecretRedaction } from "./secret-redaction.js";
|
|
5
6
|
import { createTaskTools } from "./task.js";
|
|
6
7
|
import { createJevTool } from "./jev.js";
|
|
8
|
+
import { createJevBrowserTool } from "./jev-browser.js";
|
|
7
9
|
import { createReactTool } from "./react.js";
|
|
8
10
|
import { createSandboxTool } from "./sandbox.js";
|
|
9
11
|
export { createSubagentTool } from "./subagent.js";
|
|
@@ -16,6 +18,10 @@ platformToolPackFactories = [], imageGeneration) {
|
|
|
16
18
|
const { tools: taskTools, bindTasks } = createTaskTools();
|
|
17
19
|
const { tool: reactTool, setReactFunction } = createReactTool();
|
|
18
20
|
const jevTool = createJevTool();
|
|
21
|
+
// Shells out to the operator-installed `agent-browser` CLI, which drives a
|
|
22
|
+
// real Chrome process on the host — not meaningful (and not safely
|
|
23
|
+
// reachable) from a container/image sandbox, so only host mode gets it.
|
|
24
|
+
const jevBrowserTool = executor.getSandboxConfig().type === "host" ? createJevBrowserTool() : undefined;
|
|
19
25
|
const { tool: eventTool, setEventContext } = createEventTool(eventStore);
|
|
20
26
|
const { tool: sandboxTool, setSandboxContext } = createSandboxTool(sandboxController ?? { sandbox: executor.getSandboxConfig() });
|
|
21
27
|
const platformToolPacks = platformToolPackFactories.map((createPack) => createPack());
|
|
@@ -30,9 +36,14 @@ platformToolPackFactories = [], imageGeneration) {
|
|
|
30
36
|
...(imageTool ? [adaptAgentTool(imageTool.tool)] : []),
|
|
31
37
|
adaptAgentTool(reactTool),
|
|
32
38
|
adaptAgentTool(jevTool),
|
|
39
|
+
...(jevBrowserTool ? [adaptAgentTool(jevBrowserTool)] : []),
|
|
33
40
|
...taskTools.map(adaptAgentTool),
|
|
34
41
|
...packTools.map(adaptAgentTool),
|
|
35
|
-
|
|
42
|
+
// Every tool above can return a configured secret's plain-text value —
|
|
43
|
+
// most directly bash/read in host sandbox mode, which is not OS-isolated
|
|
44
|
+
// from the mikan process's own env. Redact uniformly rather than only
|
|
45
|
+
// guarding bash.
|
|
46
|
+
].map(withSecretRedaction),
|
|
36
47
|
setUploadFunction,
|
|
37
48
|
setImageUploadFunction: (fn) => {
|
|
38
49
|
imageTool?.setUploadFunction(fn);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/harness/tools/index.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,gBAAgB,EAAE,MAAM,aAAa,CAAC;AAI/C,OAAO,EAAE,eAAe,EAAE,MAAM,YAAY,CAAC;AAC7C,OAAO,EAAE,uBAAuB,EAAE,MAAM,qBAAqB,CAAC;AAC9D,OAAO,EAAE,cAAc,EAAE,kBAAkB,EAAyB,MAAM,eAAe,CAAC;AAC1F,OAAO,EAAE,eAAe,EAAE,MAAM,WAAW,CAAC;AAC5C,OAAO,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AACzC,OAAO,EAAE,eAAe,EAAE,MAAM,YAAY,CAAC;AAC7C,OAAO,EAAE,iBAAiB,EAAE,MAAM,cAAc,CAAC;AAGjD,OAAO,EAAE,kBAAkB,EAAE,MAAM,eAAe,CAAC;AAEnD,MAAM,UAAU,gBAAgB,CAC9B,QAAkB,EAClB,UAAsB,EACtB,iBAGC;AACD;sEACsE;AACtE,yBAAyB,GAAuC,EAAE,EAClE,eAIC;IAmBD,MAAM,EAAE,IAAI,EAAE,UAAU,EAAE,iBAAiB,EAAE,GAAG,gBAAgB,EAAE,CAAC;IACnE,MAAM,SAAS,GAAG,eAAe,CAAC,CAAC,CAAC,uBAAuB,CAAC,eAAe,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;IACzF,MAAM,EAAE,KAAK,EAAE,SAAS,EAAE,SAAS,EAAE,GAAG,eAAe,EAAE,CAAC;IAC1D,MAAM,EAAE,IAAI,EAAE,SAAS,EAAE,gBAAgB,EAAE,GAAG,eAAe,EAAE,CAAC;IAChE,MAAM,OAAO,GAAG,aAAa,EAAE,CAAC;IAChC,MAAM,EAAE,IAAI,EAAE,SAAS,EAAE,eAAe,EAAE,GAAG,eAAe,CAAC,UAAU,CAAC,CAAC;IACzE,MAAM,EAAE,IAAI,EAAE,WAAW,EAAE,iBAAiB,EAAE,GAAG,iBAAiB,CAChE,iBAAiB,IAAI,EAAE,OAAO,EAAE,QAAQ,CAAC,gBAAgB,EAAE,EAAE,CAC9D,CAAC;IACF,MAAM,iBAAiB,GAAG,yBAAyB,CAAC,GAAG,CAAC,CAAC,UAAU,EAAE,EAAE,CAAC,UAAU,EAAE,CAAC,CAAC;IACtF,MAAM,SAAS,GAAG,iBAAiB,CAAC,OAAO,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;IAClE,OAAO;QACL,KAAK,EAAE;YACL,qEAAqE;YACrE,GAAG,kBAAkB,EAAE;YACvB,cAAc,CAAC,SAAS,CAAC;YACzB,cAAc,CAAC,WAAW,CAAC;YAC3B,cAAc,CAAC,UAAU,CAAC;YAC1B,GAAG,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,cAAc,CAAC,SAAS,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;YACtD,cAAc,CAAC,SAAS,CAAC;YACzB,cAAc,CAAC,OAAO,CAAC;YACvB,GAAG,SAAS,CAAC,GAAG,CAAC,cAAc,CAAC;YAChC,GAAG,SAAS,CAAC,GAAG,CAAC,cAAc,CAAC;
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/harness/tools/index.ts"],"names":[],"mappings":"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","sourcesContent":["import type { Api, Model } from \"@earendil-works/pi-ai\";\nimport type { ConversationKind } from \"../../types.js\";\nimport { createAttachTool } from \"./attach.js\";\nimport type { Executor, SandboxConfig } from \"../../sandbox/index.js\";\nimport type { OfficeAddress, SandboxResourceController } from \"../../types.js\";\nimport type { EventStore } from \"../../events/index.js\";\nimport { createEventTool } from \"./event.js\";\nimport { createGenerateImageTool } from \"./generate-image.js\";\nimport { adaptAgentTool, createSandboxTools, type MikanHarnessTool } from \"./pi-tools.js\";\nimport { withSecretRedaction } from \"./secret-redaction.js\";\nimport { createTaskTools } from \"./task.js\";\nimport { createJevTool } from \"./jev.js\";\nimport { createJevBrowserTool } from \"./jev-browser.js\";\nimport { createReactTool } from \"./react.js\";\nimport { createSandboxTool } from \"./sandbox.js\";\nimport type { PlatformToolPackFactory, PlatformToolRunContext } from \"./types.js\";\n\nexport { createSubagentTool } from \"./subagent.js\";\n\nexport function createMikanTools(\n executor: Executor,\n eventStore: EventStore,\n sandboxController?: {\n sandbox: SandboxConfig;\n resourceController?: Pick<SandboxResourceController, \"getLimitStatus\" | \"setLimits\">;\n },\n /** Platform capability pack factories (e.g. GitHub PR/CI); instantiated\n * here so each runner owns its packs' bind state. Not core tools. */\n platformToolPackFactories: readonly PlatformToolPackFactory[] = [],\n imageGeneration?: {\n model: Model<Api>;\n getApiKey: () => Promise<string | undefined>;\n outputDir: string;\n },\n): {\n tools: MikanHarnessTool[];\n setUploadFunction: (fn: (filePath: string, title?: string) => Promise<void>) => void;\n /** Upload for generate_image. Receives the file's HOST path — the tool\n * writes host-side, so this must not stage through the sandbox like the\n * attach upload does. No-op when image generation is not configured. */\n setImageUploadFunction: (fn: (hostPath: string, title?: string) => Promise<void>) => void;\n bindTasks: ReturnType<typeof createTaskTools>[\"bindTasks\"];\n setReactFunction: (fn: ((emoji: string) => Promise<void>) | null) => void;\n bindPlatformToolPacks: (ctx: PlatformToolRunContext) => void;\n setEventContext: (context: {\n platform: string;\n conversationId: string;\n conversationKind: ConversationKind;\n userId: string;\n }) => void;\n setSandboxContext: (context: { address: OfficeAddress; userId: string }) => void;\n} {\n const { tool: attachTool, setUploadFunction } = createAttachTool();\n const imageTool = imageGeneration ? createGenerateImageTool(imageGeneration) : undefined;\n const { tools: taskTools, bindTasks } = createTaskTools();\n const { tool: reactTool, setReactFunction } = createReactTool();\n const jevTool = createJevTool();\n // Shells out to the operator-installed `agent-browser` CLI, which drives a\n // real Chrome process on the host — not meaningful (and not safely\n // reachable) from a container/image sandbox, so only host mode gets it.\n const jevBrowserTool =\n executor.getSandboxConfig().type === \"host\" ? createJevBrowserTool() : undefined;\n const { tool: eventTool, setEventContext } = createEventTool(eventStore);\n const { tool: sandboxTool, setSandboxContext } = createSandboxTool(\n sandboxController ?? { sandbox: executor.getSandboxConfig() },\n );\n const platformToolPacks = platformToolPackFactories.map((createPack) => createPack());\n const packTools = platformToolPacks.flatMap((pack) => pack.tools);\n return {\n tools: [\n // pi-native read/write/edit/bash, addressed through the sandbox env.\n ...createSandboxTools(),\n adaptAgentTool(eventTool),\n adaptAgentTool(sandboxTool),\n adaptAgentTool(attachTool),\n ...(imageTool ? [adaptAgentTool(imageTool.tool)] : []),\n adaptAgentTool(reactTool),\n adaptAgentTool(jevTool),\n ...(jevBrowserTool ? [adaptAgentTool(jevBrowserTool)] : []),\n ...taskTools.map(adaptAgentTool),\n ...packTools.map(adaptAgentTool),\n // Every tool above can return a configured secret's plain-text value —\n // most directly bash/read in host sandbox mode, which is not OS-isolated\n // from the mikan process's own env. Redact uniformly rather than only\n // guarding bash.\n ].map(withSecretRedaction),\n setUploadFunction,\n setImageUploadFunction: (fn) => {\n imageTool?.setUploadFunction(fn);\n },\n setReactFunction,\n bindTasks,\n bindPlatformToolPacks: (ctx) => {\n for (const pack of platformToolPacks) {\n pack.bindRun(ctx);\n }\n },\n setEventContext,\n setSandboxContext,\n };\n}\n"]}
|
|
@@ -0,0 +1,130 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* `jev_browser`: a browser-automation tool that drives a real Chrome
|
|
3
|
+
* instance toward a natural-language goal, deciding each step itself.
|
|
4
|
+
*
|
|
5
|
+
* Combines two existing pieces rather than reimplementing either:
|
|
6
|
+
* - `agent-browser` (Vercel Labs' CLI, https://github.com/vercel-labs/agent-browser)
|
|
7
|
+
* launches and controls Chrome over CDP and produces ref-indexed
|
|
8
|
+
* accessibility snapshots (`@e1`, `@e2`, ...) — the hard part of
|
|
9
|
+
* "what's on this page and how do I click it" is already solved there.
|
|
10
|
+
* - Jev (`evaluateWithJev`, `harness/jev.ts`) picks the next operation
|
|
11
|
+
* (CLICK/TYPE_TEXT/SELECT/scroll/WAIT/DONE/BLOCKED) and its target
|
|
12
|
+
* element from that snapshot with one calibrated-choice request per
|
|
13
|
+
* step, the way github.com/browser-use/jev-ultrafast drives a browser
|
|
14
|
+
* without a full chat model in the loop.
|
|
15
|
+
*
|
|
16
|
+
* `agent-browser` is treated as an operator-installed host tool, not a
|
|
17
|
+
* mikan dependency: mikan's own `npm install --ignore-scripts` would skip
|
|
18
|
+
* its postinstall step (which downloads the platform's native binary),
|
|
19
|
+
* silently breaking it. The tool fails with an actionable error message
|
|
20
|
+
* when the CLI isn't on PATH.
|
|
21
|
+
*
|
|
22
|
+
* The Jev-driven loop only exercises the handful of agent-browser commands
|
|
23
|
+
* it needs to act on a page (open/snapshot/click/fill/select/scroll/wait).
|
|
24
|
+
* Everything else agent-browser can do — screenshot, `record start/stop`,
|
|
25
|
+
* `network har start/stop`, pdf, cookies, eval, `set viewport`, `find`,
|
|
26
|
+
* `mouse`, and any future command — is reachable through `commands`, which
|
|
27
|
+
* forwards raw argument arrays to the CLI verbatim rather than wrapping
|
|
28
|
+
* each one, so the surface stays complete as agent-browser adds commands.
|
|
29
|
+
* `session` lets a caller span such commands and a goal-driven run across
|
|
30
|
+
* multiple tool calls against the same browser (e.g. start a recording,
|
|
31
|
+
* run a goal, stop the recording, screenshot the result).
|
|
32
|
+
*
|
|
33
|
+
* v1 is intentionally minimal: no domain allowlisting, no action-policy
|
|
34
|
+
* file, no persistent auth. Host sandbox only — `index.ts` wires this tool
|
|
35
|
+
* up only when the conversation's executor reports `sandbox.type === "host"`.
|
|
36
|
+
*
|
|
37
|
+
* Session lifetime default was learned the hard way: an earlier version
|
|
38
|
+
* closed every session unless the caller passed `keepOpen: true` on *every*
|
|
39
|
+
* call, including calls that only ran `commands`. A caller reusing the same
|
|
40
|
+
* `session` id across a `record start` / goal / `record stop` sequence
|
|
41
|
+
* forgot that flag on most calls, so each call silently closed and
|
|
42
|
+
* reopened a brand-new browser under the same session name — `record
|
|
43
|
+
* start` ran, the browser closed before any frame was captured, the next
|
|
44
|
+
* call's `record stop` had nothing to stop, and `network har
|
|
45
|
+
* start`/`stop` bracketed zero continuous browsing time. The failure was
|
|
46
|
+
* silent: every individual call still reported success. Now the default
|
|
47
|
+
* follows the caller's stated intent instead of a flag that is easy to
|
|
48
|
+
* forget under focus on harder problems (what to click, how long to wait
|
|
49
|
+
* for an intermittent element): naming an existing `session` means "keep
|
|
50
|
+
* this browser around," so the tool does not close it unless `close: true`
|
|
51
|
+
* is explicit. Only a call with no `session` (a one-off, auto-generated
|
|
52
|
+
* session) closes by default, preserving the original single-call
|
|
53
|
+
* ergonomics. The downside — a one-off call that happens to pass an
|
|
54
|
+
* explicit `session` name without ever reusing it leaves that session
|
|
55
|
+
* lingering — is bounded by agent-browser's own 1-hour idle-daemon
|
|
56
|
+
* timeout and is strictly safer than silently destroying in-progress
|
|
57
|
+
* capture state.
|
|
58
|
+
*
|
|
59
|
+
* Every result also reports `browserContinuity`, a one-line readable
|
|
60
|
+
* summary of whether the browser that just ran was actually the same one
|
|
61
|
+
* as the prior call in this session (agent-browser's own `reused` /
|
|
62
|
+
* `relaunchedBrowser` / `launched` lifecycle fields, otherwise buried a
|
|
63
|
+
* few levels deep inside each raw `commandResults` entry) — so a caller
|
|
64
|
+
* debugging a capture that came back empty sees "the browser was
|
|
65
|
+
* relaunched, not continuous" directly, instead of only suspecting it
|
|
66
|
+
* after reading raw JSON for several turns.
|
|
67
|
+
*
|
|
68
|
+
* The Jev-driven loop only decides actions; it does not summarize or
|
|
69
|
+
* extract page content itself. Its result always carries
|
|
70
|
+
* `lastPageSnapshot`, the accessibility-tree text of the last page
|
|
71
|
+
* observed — including a run that reaches DONE on the very first
|
|
72
|
+
* snapshot, whose `history` is empty. Without this, the caller has no way
|
|
73
|
+
* to read what the browser actually saw, and reaches for an unrelated
|
|
74
|
+
* tool (e.g. `curl`) to get an answer this tool already had.
|
|
75
|
+
*/
|
|
76
|
+
import type { AgentTool } from "@earendil-works/pi-agent-core";
|
|
77
|
+
import { type JevQuestions } from "../jev.js";
|
|
78
|
+
declare const jevBrowserSchema: import("@sinclair/typebox").TObject<{
|
|
79
|
+
label: import("@sinclair/typebox").TString;
|
|
80
|
+
goal: import("@sinclair/typebox").TOptional<import("@sinclair/typebox").TString>;
|
|
81
|
+
url: import("@sinclair/typebox").TOptional<import("@sinclair/typebox").TString>;
|
|
82
|
+
commands: import("@sinclair/typebox").TOptional<import("@sinclair/typebox").TArray<import("@sinclair/typebox").TArray<import("@sinclair/typebox").TString>>>;
|
|
83
|
+
session: import("@sinclair/typebox").TOptional<import("@sinclair/typebox").TString>;
|
|
84
|
+
close: import("@sinclair/typebox").TOptional<import("@sinclair/typebox").TBoolean>;
|
|
85
|
+
maxSteps: import("@sinclair/typebox").TOptional<import("@sinclair/typebox").TInteger>;
|
|
86
|
+
}>;
|
|
87
|
+
interface RefInfo {
|
|
88
|
+
role: string;
|
|
89
|
+
name: string;
|
|
90
|
+
}
|
|
91
|
+
/** Present on `data` in every agent-browser response, regardless of command. */
|
|
92
|
+
interface BrowserLifecycle {
|
|
93
|
+
reused?: boolean;
|
|
94
|
+
relaunchedBrowser?: boolean;
|
|
95
|
+
launched?: boolean;
|
|
96
|
+
}
|
|
97
|
+
/**
|
|
98
|
+
* One-line, non-buried answer to "was this call's browser actually the
|
|
99
|
+
* same one a prior call in this session left running?" — built from the
|
|
100
|
+
* first agent-browser response in this invocation. Answers the question a
|
|
101
|
+
* caller debugging an empty recording/HAR needs first, before it occurs to
|
|
102
|
+
* them to go digging through commandResults' raw lifecycle fields.
|
|
103
|
+
*/
|
|
104
|
+
declare function describeContinuity(hadSession: boolean, first: BrowserLifecycle | undefined): string;
|
|
105
|
+
declare function truncate(text: string, max: number): string;
|
|
106
|
+
/** Split refs into candidate buckets per operation. CLICK accepts any ref. */
|
|
107
|
+
declare function categorizeRefs(refs: Record<string, RefInfo>): {
|
|
108
|
+
click: [string, RefInfo][];
|
|
109
|
+
type: [string, RefInfo][];
|
|
110
|
+
select: [string, RefInfo][];
|
|
111
|
+
};
|
|
112
|
+
interface QuestionPlan {
|
|
113
|
+
questions: JevQuestions;
|
|
114
|
+
/** Operations whose only candidate is resolved directly, with no target question. */
|
|
115
|
+
singles: Record<string, string>;
|
|
116
|
+
}
|
|
117
|
+
/**
|
|
118
|
+
* Build the per-step Jev request: one `operation` choice (always present)
|
|
119
|
+
* plus a `*_target` choice for every operation with 2+ candidate refs.
|
|
120
|
+
* An operation with exactly one candidate skips the target question —
|
|
121
|
+
* Jev's `choice` questions require at least two options — and resolves to
|
|
122
|
+
* that ref directly once selected.
|
|
123
|
+
*/
|
|
124
|
+
declare function buildQuestionPlan(refs: Record<string, RefInfo>, canScrollUp: boolean, canScrollDown: boolean): QuestionPlan;
|
|
125
|
+
declare function resolveTarget(operation: string, answers: Record<string, {
|
|
126
|
+
choice?: unknown;
|
|
127
|
+
} | undefined>, singles: Record<string, string>): string | undefined;
|
|
128
|
+
export declare function createJevBrowserTool(): AgentTool<typeof jevBrowserSchema>;
|
|
129
|
+
export { buildQuestionPlan, resolveTarget, categorizeRefs, truncate, describeContinuity };
|
|
130
|
+
//# sourceMappingURL=jev-browser.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"jev-browser.d.ts","sourceRoot":"","sources":["../../../src/harness/tools/jev-browser.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA0EG;AACH,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,+BAA+B,CAAC;AAM/D,OAAO,EAAkC,KAAK,YAAY,EAAE,MAAM,WAAW,CAAC;AAc9E,QAAA,MAAM,gBAAgB;;;;;;;;EAuCpB,CAAC;AAIH,UAAU,OAAO;IACf,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC;CACd;AAcD,gFAAgF;AAChF,UAAU,gBAAgB;IACxB,MAAM,CAAC,EAAE,OAAO,CAAC;IACjB,iBAAiB,CAAC,EAAE,OAAO,CAAC;IAC5B,QAAQ,CAAC,EAAE,OAAO,CAAC;CACpB;AAMD;;;;;;GAMG;AACH,iBAAS,kBAAkB,CAAC,UAAU,EAAE,OAAO,EAAE,KAAK,EAAE,gBAAgB,GAAG,SAAS,GAAG,MAAM,CAa5F;AAgCD,iBAAS,QAAQ,CAAC,IAAI,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,GAAG,MAAM,CAEnD;AAiCD,8EAA8E;AAC9E,iBAAS,cAAc,CAAC,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG;IACtD,KAAK,EAAE,CAAC,MAAM,EAAE,OAAO,CAAC,EAAE,CAAC;IAC3B,IAAI,EAAE,CAAC,MAAM,EAAE,OAAO,CAAC,EAAE,CAAC;IAC1B,MAAM,EAAE,CAAC,MAAM,EAAE,OAAO,CAAC,EAAE,CAAC;CAC7B,CAOA;AASD,UAAU,YAAY;IACpB,SAAS,EAAE,YAAY,CAAC;IACxB,qFAAqF;IACrF,OAAO,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;CACjC;AAED;;;;;;GAMG;AACH,iBAAS,iBAAiB,CACxB,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAC7B,WAAW,EAAE,OAAO,EACpB,aAAa,EAAE,OAAO,GACrB,YAAY,CAgDd;AAsDD,iBAAS,aAAa,CACpB,SAAS,EAAE,MAAM,EACjB,OAAO,EAAE,MAAM,CAAC,MAAM,EAAE;IAAE,MAAM,CAAC,EAAE,OAAO,CAAA;CAAE,GAAG,SAAS,CAAC,EACzD,OAAO,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAC9B,MAAM,GAAG,SAAS,CAUpB;AAED,wBAAgB,oBAAoB,IAAI,SAAS,CAAC,OAAO,gBAAgB,CAAC,CAuPzE;AAGD,OAAO,EAAE,iBAAiB,EAAE,aAAa,EAAE,cAAc,EAAE,QAAQ,EAAE,kBAAkB,EAAE,CAAC"}
|