pi-agent-browser-native 0.2.45 → 0.2.46
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 +16 -0
- package/extensions/agent-browser/index.ts +17 -8
- package/extensions/agent-browser/lib/input-modes/params.ts +11 -4
- package/extensions/agent-browser/lib/json-schema.ts +73 -0
- package/extensions/agent-browser/lib/orchestration/browser-run/diagnostics.ts +6 -0
- package/extensions/agent-browser/lib/pi-tool-rendering.ts +28 -7
- package/extensions/agent-browser/lib/string-enum-schema.ts +20 -0
- package/extensions/agent-browser/lib/web-search.ts +30 -12
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -4,6 +4,22 @@
|
|
|
4
4
|
|
|
5
5
|
No changes yet.
|
|
6
6
|
|
|
7
|
+
## 0.2.46 - 2026-06-07
|
|
8
|
+
|
|
9
|
+
### Changed
|
|
10
|
+
|
|
11
|
+
- Reduced native extension startup cost by replacing heavy top-level Pi and TypeBox runtime imports with lightweight local schema and event helpers while preserving the public tool schemas.
|
|
12
|
+
- Kept custom browser tool rendering compact without importing Pi's full coding-agent runtime during extension load.
|
|
13
|
+
|
|
14
|
+
### Fixed
|
|
15
|
+
|
|
16
|
+
- Fixed issue #84 by cutting local cold extension import plus factory registration from roughly 1.1 seconds to roughly 76 milliseconds in checkout measurements.
|
|
17
|
+
- Stabilized timeout partial-progress diagnostics so post-navigation timeouts are recognized from later completed-step evidence even when live URL recovery is unavailable under load.
|
|
18
|
+
|
|
19
|
+
### Validation
|
|
20
|
+
|
|
21
|
+
- Added a cold-start budget test for the real extension entrypoint, schema parity coverage against the canonical TypeBox/StringEnum builders, rendering coverage for JSON highlighting plus collapsed-output expand hints, and stabilized deterministic dogfood smoke by avoiding a rapid Windows browser close/relaunch race.
|
|
22
|
+
|
|
7
23
|
## 0.2.45 - 2026-06-06
|
|
8
24
|
|
|
9
25
|
### Added
|
|
@@ -10,11 +10,10 @@ import type { ChildProcess } from "node:child_process";
|
|
|
10
10
|
import { dirname, join, resolve } from "node:path";
|
|
11
11
|
import { fileURLToPath } from "node:url";
|
|
12
12
|
|
|
13
|
-
import {
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
type ExtensionContext,
|
|
13
|
+
import type {
|
|
14
|
+
AgentToolResult,
|
|
15
|
+
ExtensionAPI,
|
|
16
|
+
ExtensionContext,
|
|
18
17
|
} from "@earendil-works/pi-coding-agent";
|
|
19
18
|
import { Text } from "@earendil-works/pi-tui";
|
|
20
19
|
import {
|
|
@@ -91,7 +90,7 @@ import {
|
|
|
91
90
|
restoreElectronLaunchRecordsFromBranch,
|
|
92
91
|
type ElectronLaunchRecord,
|
|
93
92
|
} from "./lib/orchestration/electron-host/index.js";
|
|
94
|
-
import { buildValidationFailureResult, resolveAgentBrowserInput } from "./lib/orchestration/input-plan.js";
|
|
93
|
+
import { buildValidationFailureResult, resolveAgentBrowserInput, type AgentBrowserExecuteParams } from "./lib/orchestration/input-plan.js";
|
|
95
94
|
import { applyAgentBrowserOutputPath } from "./lib/orchestration/output-file.js";
|
|
96
95
|
import type { NetworkRouteRecord } from "./lib/results/contracts.js";
|
|
97
96
|
import type { SessionArtifactManifest } from "./lib/results/contracts.js";
|
|
@@ -131,6 +130,16 @@ import {
|
|
|
131
130
|
|
|
132
131
|
const DEFAULT_SESSION_MODE = "auto" as const;
|
|
133
132
|
|
|
133
|
+
type BashToolCallLike = {
|
|
134
|
+
input: { command: string };
|
|
135
|
+
toolName: "bash";
|
|
136
|
+
};
|
|
137
|
+
|
|
138
|
+
function isBashToolCallEvent(event: unknown): event is BashToolCallLike {
|
|
139
|
+
if (!isRecord(event) || event.toolName !== "bash" || !isRecord(event.input)) return false;
|
|
140
|
+
return typeof event.input.command === "string";
|
|
141
|
+
}
|
|
142
|
+
|
|
134
143
|
type OwnedManagedSession = {
|
|
135
144
|
branchOwned: boolean;
|
|
136
145
|
cwd: string;
|
|
@@ -753,7 +762,7 @@ export default function agentBrowserExtension(pi: ExtensionAPI) {
|
|
|
753
762
|
pi.on("tool_call", async (event, ctx) => {
|
|
754
763
|
const promptPolicy = buildPromptPolicy(getLatestUserPrompt(ctx.sessionManager.getBranch()));
|
|
755
764
|
if (
|
|
756
|
-
|
|
765
|
+
isBashToolCallEvent(event) &&
|
|
757
766
|
!promptPolicy.allowLegacyAgentBrowserBash &&
|
|
758
767
|
looksLikeDirectAgentBrowserBash(event.input.command) &&
|
|
759
768
|
!isHarmlessAgentBrowserInspectionCommand(event.input.command) &&
|
|
@@ -789,7 +798,7 @@ export default function agentBrowserExtension(pi: ExtensionAPI) {
|
|
|
789
798
|
component.setState(formatAgentBrowserRenderResult(result, options, theme, context.isError), options.expanded, theme);
|
|
790
799
|
return component;
|
|
791
800
|
},
|
|
792
|
-
async execute(_toolCallId, params, signal, onUpdate, ctx) {
|
|
801
|
+
async execute(_toolCallId, params: AgentBrowserExecuteParams, signal, onUpdate, ctx) {
|
|
793
802
|
const promptPolicy = buildPromptPolicy(getLatestUserPrompt(ctx.sessionManager.getBranch()));
|
|
794
803
|
const outputPath = isRecord(params) && typeof params.outputPath === "string" ? params.outputPath : undefined;
|
|
795
804
|
const resolvedInput = resolveAgentBrowserInput({
|
|
@@ -4,8 +4,8 @@
|
|
|
4
4
|
* Scope: Schema-only; behavioral validation lives in the mode compilers.
|
|
5
5
|
*/
|
|
6
6
|
|
|
7
|
-
import {
|
|
8
|
-
import {
|
|
7
|
+
import { JsonSchema, type JsonSchemaBuilder } from "../json-schema.js";
|
|
8
|
+
import { StringEnum as localStringEnum, type StringEnumBuilder } from "../string-enum-schema.js";
|
|
9
9
|
|
|
10
10
|
import {
|
|
11
11
|
ELECTRON_DISCOVERY_DEFAULT_MAX_RESULTS,
|
|
@@ -23,7 +23,11 @@ import {
|
|
|
23
23
|
SOURCE_LOOKUP_MAX_WORKSPACE_FILES,
|
|
24
24
|
} from "./types.js";
|
|
25
25
|
|
|
26
|
-
export
|
|
26
|
+
export function createAgentBrowserParamsSchema(
|
|
27
|
+
Type: JsonSchemaBuilder = JsonSchema,
|
|
28
|
+
StringEnum: StringEnumBuilder = localStringEnum,
|
|
29
|
+
) {
|
|
30
|
+
return Type.Object({
|
|
27
31
|
|
|
28
32
|
args: Type.Optional(
|
|
29
33
|
Type.Array(Type.String({ description: "Exact agent-browser CLI arguments, excluding the binary name. Do not pass --json; the wrapper injects it. First-call recipe: open → snapshot -i → click/fill @eN → snapshot -i." }), {
|
|
@@ -195,4 +199,7 @@ export const AGENT_BROWSER_PARAMS = Type.Object({
|
|
|
195
199
|
default: DEFAULT_SESSION_MODE,
|
|
196
200
|
}),
|
|
197
201
|
),
|
|
198
|
-
}, { additionalProperties: false });
|
|
202
|
+
}, { additionalProperties: false });
|
|
203
|
+
}
|
|
204
|
+
|
|
205
|
+
export const AGENT_BROWSER_PARAMS = createAgentBrowserParamsSchema();
|
|
@@ -0,0 +1,73 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Purpose: Build the small JSON Schema subset used by Pi tool schemas without importing TypeBox at runtime.
|
|
3
|
+
* Responsibilities: Preserve plain JSON Schema objects Pi consumes while keeping extension startup cheap.
|
|
4
|
+
* Scope: Schema construction only; runtime validation still belongs to Pi and the tool input compilers.
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
import type { TSchema, TSchemaOptions, TUnsafe } from "typebox";
|
|
8
|
+
|
|
9
|
+
const OPTIONAL_SCHEMA = Symbol("pi-agent-browser-optional-schema");
|
|
10
|
+
|
|
11
|
+
type SchemaObject = TSchema & { [OPTIONAL_SCHEMA]?: true };
|
|
12
|
+
type SchemaProperties = Record<string, TSchema>;
|
|
13
|
+
|
|
14
|
+
function withOptions(schema: Record<string, unknown>, options?: TSchemaOptions): TSchema {
|
|
15
|
+
return { ...schema, ...(options ?? {}) } as TSchema;
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
function literalType(value: unknown): "boolean" | "number" | "string" | undefined {
|
|
19
|
+
const valueType = typeof value;
|
|
20
|
+
return valueType === "string" || valueType === "number" || valueType === "boolean" ? valueType : undefined;
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
function propertySchema(schema: TSchema): TSchema {
|
|
24
|
+
const clone = { ...(schema as SchemaObject & Record<PropertyKey, unknown>) };
|
|
25
|
+
delete clone[OPTIONAL_SCHEMA];
|
|
26
|
+
return clone as TSchema;
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
export const JsonSchema = {
|
|
30
|
+
Array(items: TSchema, options?: TSchemaOptions): TSchema {
|
|
31
|
+
return withOptions({ type: "array", items }, options);
|
|
32
|
+
},
|
|
33
|
+
Boolean(options?: TSchemaOptions): TSchema {
|
|
34
|
+
return withOptions({ type: "boolean" }, options);
|
|
35
|
+
},
|
|
36
|
+
Integer(options?: TSchemaOptions): TSchema {
|
|
37
|
+
return withOptions({ type: "integer" }, options);
|
|
38
|
+
},
|
|
39
|
+
Literal(value: unknown, options?: TSchemaOptions): TSchema {
|
|
40
|
+
const type = literalType(value);
|
|
41
|
+
return withOptions(type ? { type, const: value } : { const: value }, options);
|
|
42
|
+
},
|
|
43
|
+
Number(options?: TSchemaOptions): TSchema {
|
|
44
|
+
return withOptions({ type: "number" }, options);
|
|
45
|
+
},
|
|
46
|
+
Object(properties: SchemaProperties, options?: TSchemaOptions): TSchema {
|
|
47
|
+
const required = globalThis.Object.entries(properties)
|
|
48
|
+
.filter(([, schema]) => (schema as SchemaObject)[OPTIONAL_SCHEMA] !== true)
|
|
49
|
+
.map(([key]) => key);
|
|
50
|
+
return withOptions({
|
|
51
|
+
type: "object",
|
|
52
|
+
properties: globalThis.Object.fromEntries(
|
|
53
|
+
globalThis.Object.entries(properties).map(([key, schema]) => [key, propertySchema(schema)]),
|
|
54
|
+
),
|
|
55
|
+
...(required.length > 0 ? { required } : {}),
|
|
56
|
+
}, options);
|
|
57
|
+
},
|
|
58
|
+
Optional(schema: TSchema): TSchema {
|
|
59
|
+
return { ...(schema as SchemaObject), [OPTIONAL_SCHEMA]: true } as TSchema;
|
|
60
|
+
},
|
|
61
|
+
String(options?: TSchemaOptions): TSchema {
|
|
62
|
+
return withOptions({ type: "string" }, options);
|
|
63
|
+
},
|
|
64
|
+
Union(types: TSchema[], options?: TSchemaOptions): TSchema {
|
|
65
|
+
return withOptions({ anyOf: types }, options);
|
|
66
|
+
},
|
|
67
|
+
Unsafe<Value>(schema: TSchema): TUnsafe<Value> {
|
|
68
|
+
return schema as TUnsafe<Value>;
|
|
69
|
+
},
|
|
70
|
+
};
|
|
71
|
+
|
|
72
|
+
export type JsonSchemaBuilder = typeof JsonSchema;
|
|
73
|
+
export type { TSchema, TSchemaOptions, TUnsafe };
|
|
@@ -824,6 +824,12 @@ function buildTimeoutProgressSteps(options: {
|
|
|
824
824
|
step.reason = "Later step completion evidence indicates the batch advanced past this step before timeout.";
|
|
825
825
|
}
|
|
826
826
|
}
|
|
827
|
+
for (const step of progressSteps) {
|
|
828
|
+
const command = step.args[0];
|
|
829
|
+
if (step.status === "completed" && (isOpenNavigationCommand(command) || command === "pushstate")) {
|
|
830
|
+
lastCompletedNavigationIndex = Math.max(lastCompletedNavigationIndex ?? 0, step.index);
|
|
831
|
+
}
|
|
832
|
+
}
|
|
827
833
|
for (const step of progressSteps) {
|
|
828
834
|
if (step.status === "completed") continue;
|
|
829
835
|
if (!retryStep) {
|
|
@@ -1,6 +1,5 @@
|
|
|
1
1
|
import type { AgentToolResult, Theme, ToolResultEvent } from "@earendil-works/pi-coding-agent";
|
|
2
|
-
import {
|
|
3
|
-
import { Text, truncateToWidth } from "@earendil-works/pi-tui";
|
|
2
|
+
import { getKeybindings, Text, truncateToWidth } from "@earendil-works/pi-tui";
|
|
4
3
|
|
|
5
4
|
import {
|
|
6
5
|
compileAgentBrowserElectron,
|
|
@@ -16,6 +15,7 @@ import { redactInvocationArgs } from "./runtime.js";
|
|
|
16
15
|
const TUI_INVOCATION_PREVIEW_MAX_CHARS = 160;
|
|
17
16
|
const TUI_COLLAPSED_OUTPUT_MAX_LINES = 12;
|
|
18
17
|
const ANSI_CONTROL_SEQUENCE_PATTERN = /\x1B(?:\][^\x07\x1B]*(?:\x07|\x1B\\)|\[[0-?]*[ -/]*[@-~]|P[^\x1B]*(?:\x1B\\)|_[^\x1B]*(?:\x1B\\)|\^[^\x1B]*(?:\x1B\\)|[@-Z\\-_])/g;
|
|
18
|
+
const JSON_TOKEN_PATTERN = /"(?:\\.|[^"\\])*"(?=\s*:)|"(?:\\.|[^"\\])*"|-?\d+(?:\.\d+)?(?:[eE][+-]?\d+)?|true|false|null|[{}\[\],:]/g;
|
|
19
19
|
const UNSAFE_DISPLAY_CONTROL_PATTERN = /[\x00-\x08\x0B\x0C\x0E-\x1F\x7F\x80-\x9F]/g;
|
|
20
20
|
|
|
21
21
|
function sanitizeDisplayText(value: string): string {
|
|
@@ -48,6 +48,26 @@ function isJsonDocumentText(value: string): boolean {
|
|
|
48
48
|
}
|
|
49
49
|
}
|
|
50
50
|
|
|
51
|
+
function colorizeJsonLine(line: string, theme: Theme): string {
|
|
52
|
+
let output = "";
|
|
53
|
+
let cursor = 0;
|
|
54
|
+
for (const match of line.matchAll(JSON_TOKEN_PATTERN)) {
|
|
55
|
+
const token = match[0];
|
|
56
|
+
const index = match.index ?? 0;
|
|
57
|
+
output += line.slice(cursor, index);
|
|
58
|
+
const color = token.startsWith('"')
|
|
59
|
+
? /"\s*$/.test(token) && line.slice(index + token.length).trimStart().startsWith(":")
|
|
60
|
+
? "syntaxVariable"
|
|
61
|
+
: "syntaxString"
|
|
62
|
+
: /^[{}\[\],:]$/.test(token)
|
|
63
|
+
? "syntaxPunctuation"
|
|
64
|
+
: "syntaxType";
|
|
65
|
+
output += theme.fg(color, token);
|
|
66
|
+
cursor = index + token.length;
|
|
67
|
+
}
|
|
68
|
+
return output + line.slice(cursor);
|
|
69
|
+
}
|
|
70
|
+
|
|
51
71
|
function getPrimaryTextContent(result: AgentToolResult<unknown>): string {
|
|
52
72
|
const textContent = result.content.find((item) => item.type === "text");
|
|
53
73
|
return textContent?.type === "text" ? textContent.text : "";
|
|
@@ -57,23 +77,24 @@ function colorizeToolOutputLines(outputText: string, theme: Theme, isError: bool
|
|
|
57
77
|
const normalizedLines = trimTrailingBlankLines(replaceTabsForDisplay(sanitizeDisplayText(outputText)).split("\n"));
|
|
58
78
|
const normalizedText = normalizedLines.join("\n");
|
|
59
79
|
if (normalizedText.length === 0) return [];
|
|
60
|
-
|
|
61
|
-
return highlightCode(normalizedText, "json");
|
|
62
|
-
}
|
|
80
|
+
const isJsonDocument = !isError && isJsonDocumentText(normalizedText);
|
|
63
81
|
return normalizedLines.map((line) => {
|
|
64
82
|
if (line.length === 0) {
|
|
65
83
|
return "";
|
|
66
84
|
}
|
|
85
|
+
if (isJsonDocument) return colorizeJsonLine(line, theme);
|
|
67
86
|
return isError ? theme.fg("error", line) : theme.fg("toolOutput", line);
|
|
68
87
|
});
|
|
69
88
|
}
|
|
70
89
|
|
|
71
90
|
function formatExpandHint(theme: Theme): string {
|
|
72
91
|
try {
|
|
73
|
-
|
|
92
|
+
const [key] = getKeybindings().getKeys("app.tools.expand" as never);
|
|
93
|
+
if (key) return `${theme.fg("dim", key)} ${theme.fg("muted", "to expand")}`;
|
|
74
94
|
} catch {
|
|
75
|
-
|
|
95
|
+
// Fall through to the built-in default key when coding-agent keybindings are unavailable.
|
|
76
96
|
}
|
|
97
|
+
return `${theme.fg("dim", "ctrl+o")} ${theme.fg("muted", "to expand")}`;
|
|
77
98
|
}
|
|
78
99
|
|
|
79
100
|
function formatVisualTruncationNotice(remainingLines: number, totalLines: number, theme: Theme, width: number): string {
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Purpose: Build compact JSON-schema string enums without importing pi runtime helpers.
|
|
3
|
+
* Responsibilities: Mirror pi-ai StringEnum's `{ type: "string", enum: [...] }` shape while keeping extension startup imports light.
|
|
4
|
+
* Scope: Schema construction only.
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
import { JsonSchema, type TSchemaOptions, type TUnsafe } from "./json-schema.js";
|
|
8
|
+
|
|
9
|
+
export type StringEnumBuilder = typeof StringEnum;
|
|
10
|
+
|
|
11
|
+
export function StringEnum<const Values extends readonly string[]>(
|
|
12
|
+
values: Values,
|
|
13
|
+
options?: TSchemaOptions,
|
|
14
|
+
): TUnsafe<Values[number]> {
|
|
15
|
+
return JsonSchema.Unsafe<Values[number]>({
|
|
16
|
+
type: "string",
|
|
17
|
+
enum: [...values],
|
|
18
|
+
...options,
|
|
19
|
+
});
|
|
20
|
+
}
|
|
@@ -4,9 +4,8 @@
|
|
|
4
4
|
* Scope: Live web search only; browser automation remains in the `agent_browser` tool.
|
|
5
5
|
*/
|
|
6
6
|
|
|
7
|
-
import {
|
|
8
|
-
import {
|
|
9
|
-
import { Type } from "typebox";
|
|
7
|
+
import { JsonSchema, type JsonSchemaBuilder } from "./json-schema.js";
|
|
8
|
+
import { StringEnum as localStringEnum, type StringEnumBuilder } from "./string-enum-schema.js";
|
|
10
9
|
import {
|
|
11
10
|
DEFAULT_WEB_SEARCH_PROVIDER,
|
|
12
11
|
WEB_SEARCH_PROVIDERS,
|
|
@@ -119,8 +118,12 @@ export interface WebSearchProviderAdapter<Request = unknown, Response = unknown>
|
|
|
119
118
|
provider: WebSearchProvider;
|
|
120
119
|
}
|
|
121
120
|
|
|
122
|
-
export
|
|
123
|
-
|
|
121
|
+
export function createAgentBrowserWebSearchParamsSchema(
|
|
122
|
+
Type: JsonSchemaBuilder = JsonSchema,
|
|
123
|
+
StringEnum: StringEnumBuilder = localStringEnum,
|
|
124
|
+
) {
|
|
125
|
+
return Type.Object(
|
|
126
|
+
{
|
|
124
127
|
query: Type.String({
|
|
125
128
|
minLength: 1,
|
|
126
129
|
description: "Search query to run with the configured Exa or Brave web search provider.",
|
|
@@ -172,9 +175,12 @@ export const AgentBrowserWebSearchParams = Type.Object(
|
|
|
172
175
|
description: "Optional freshness window: pd=past day, pw=past week, pm=past month, py=past year.",
|
|
173
176
|
}),
|
|
174
177
|
),
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
);
|
|
178
|
+
},
|
|
179
|
+
{ additionalProperties: false },
|
|
180
|
+
);
|
|
181
|
+
}
|
|
182
|
+
|
|
183
|
+
export const AgentBrowserWebSearchParams = createAgentBrowserWebSearchParamsSchema();
|
|
178
184
|
|
|
179
185
|
const HTML_ENTITY_REPLACEMENTS: Readonly<Record<string, string>> = {
|
|
180
186
|
amp: "&",
|
|
@@ -644,9 +650,21 @@ function buildMissingCredentialError(provider: WebSearchProviderParam): string {
|
|
|
644
650
|
return "No Exa or Brave web search credential resolved. Configure webSearch.exaApiKey or webSearch.braveApiKey, or load EXA_API_KEY/BRAVE_API_KEY in the runtime environment.";
|
|
645
651
|
}
|
|
646
652
|
|
|
653
|
+
type AgentBrowserWebSearchParamsInput = {
|
|
654
|
+
country?: string;
|
|
655
|
+
count?: number;
|
|
656
|
+
freshness?: SearchFreshness;
|
|
657
|
+
offset?: number;
|
|
658
|
+
provider?: WebSearchProviderParam;
|
|
659
|
+
query: string;
|
|
660
|
+
safesearch?: "off" | "moderate" | "strict";
|
|
661
|
+
searchLang?: string;
|
|
662
|
+
searchType?: ExaSearchType;
|
|
663
|
+
};
|
|
664
|
+
|
|
647
665
|
export function createAgentBrowserWebSearchTool(configState: AgentBrowserConfigState) {
|
|
648
666
|
const requestGate = new WebSearchRequestGate();
|
|
649
|
-
return
|
|
667
|
+
return {
|
|
650
668
|
name: AGENT_BROWSER_WEB_SEARCH_TOOL_NAME,
|
|
651
669
|
label: "Agent Browser Web Search",
|
|
652
670
|
description: `Search the web with Exa or Brave when configured. Returns up to ${MAX_SEARCH_RESULT_COUNT} concise web results.`,
|
|
@@ -659,7 +677,7 @@ export function createAgentBrowserWebSearchTool(configState: AgentBrowserConfigS
|
|
|
659
677
|
"After using agent_browser_web_search, cite result URLs in the final answer when web evidence informed the answer.",
|
|
660
678
|
],
|
|
661
679
|
parameters: AgentBrowserWebSearchParams,
|
|
662
|
-
async execute(_toolCallId, params, signal) {
|
|
680
|
+
async execute(_toolCallId: string, params: AgentBrowserWebSearchParamsInput, signal?: AbortSignal) {
|
|
663
681
|
if (!configState.webSearchEnabled) {
|
|
664
682
|
throw new Error("agent_browser_web_search is disabled by pi-agent-browser-native config.");
|
|
665
683
|
}
|
|
@@ -695,9 +713,9 @@ export function createAgentBrowserWebSearchTool(configState: AgentBrowserConfigS
|
|
|
695
713
|
results: normalized.results,
|
|
696
714
|
};
|
|
697
715
|
return {
|
|
698
|
-
content: [{ type: "text", text: formatSearchResults(adapter.provider, normalized.returnedQuery, normalized.results) }],
|
|
716
|
+
content: [{ type: "text" as const, text: formatSearchResults(adapter.provider, normalized.returnedQuery, normalized.results) }],
|
|
699
717
|
details,
|
|
700
718
|
};
|
|
701
719
|
},
|
|
702
|
-
}
|
|
720
|
+
};
|
|
703
721
|
}
|
package/package.json
CHANGED