pi-agent-browser-native 0.2.48 → 0.2.49

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.
Files changed (185) hide show
  1. package/CHANGELOG.md +17 -0
  2. package/README.md +16 -6
  3. package/dist/extensions/agent-browser/index.js +785 -0
  4. package/dist/extensions/agent-browser/lib/argv-descriptor.js +71 -0
  5. package/dist/extensions/agent-browser/lib/argv-grammar.js +121 -0
  6. package/dist/extensions/agent-browser/lib/bash-guard.js +190 -0
  7. package/dist/extensions/agent-browser/lib/command-policy.js +85 -0
  8. package/dist/extensions/agent-browser/lib/command-taxonomy.js +302 -0
  9. package/dist/extensions/agent-browser/lib/config-policy.js +686 -0
  10. package/dist/extensions/agent-browser/lib/config.js +122 -0
  11. package/dist/extensions/agent-browser/lib/electron/cdp.js +51 -0
  12. package/dist/extensions/agent-browser/lib/electron/cleanup.js +212 -0
  13. package/dist/extensions/agent-browser/lib/electron/discovery.js +633 -0
  14. package/dist/extensions/agent-browser/lib/electron/launch.js +351 -0
  15. package/{extensions/agent-browser/lib/electron/text.ts → dist/extensions/agent-browser/lib/electron/text.js} +5 -5
  16. package/dist/extensions/agent-browser/lib/executable-path.js +20 -0
  17. package/dist/extensions/agent-browser/lib/fs-utils.js +18 -0
  18. package/dist/extensions/agent-browser/lib/input-modes/electron.js +165 -0
  19. package/dist/extensions/agent-browser/lib/input-modes/job.js +519 -0
  20. package/dist/extensions/agent-browser/lib/input-modes/lookups.js +440 -0
  21. package/dist/extensions/agent-browser/lib/input-modes/params.js +164 -0
  22. package/dist/extensions/agent-browser/lib/input-modes/semantic-action.js +119 -0
  23. package/dist/extensions/agent-browser/lib/input-modes/shared.js +42 -0
  24. package/dist/extensions/agent-browser/lib/input-modes/types.js +21 -0
  25. package/dist/extensions/agent-browser/lib/input-modes.js +10 -0
  26. package/dist/extensions/agent-browser/lib/json-schema.js +58 -0
  27. package/dist/extensions/agent-browser/lib/launch-scoped-flags.js +59 -0
  28. package/dist/extensions/agent-browser/lib/navigation-policy.js +83 -0
  29. package/dist/extensions/agent-browser/lib/orchestration/batch-stdin.js +62 -0
  30. package/dist/extensions/agent-browser/lib/orchestration/browser-run/artifact-paths.js +39 -0
  31. package/dist/extensions/agent-browser/lib/orchestration/browser-run/click-dispatch.js +276 -0
  32. package/dist/extensions/agent-browser/lib/orchestration/browser-run/diagnostics.js +909 -0
  33. package/dist/extensions/agent-browser/lib/orchestration/browser-run/final-result.js +443 -0
  34. package/dist/extensions/agent-browser/lib/orchestration/browser-run/index.js +47 -0
  35. package/dist/extensions/agent-browser/lib/orchestration/browser-run/prepare/direct-anchor-download.js +141 -0
  36. package/dist/extensions/agent-browser/lib/orchestration/browser-run/prepare/network-page-filter.js +108 -0
  37. package/dist/extensions/agent-browser/lib/orchestration/browser-run/prepare/scroll-shims.js +112 -0
  38. package/dist/extensions/agent-browser/lib/orchestration/browser-run/prepare/snapshot-filter.js +158 -0
  39. package/dist/extensions/agent-browser/lib/orchestration/browser-run/prepare/wait-timeouts.js +54 -0
  40. package/dist/extensions/agent-browser/lib/orchestration/browser-run/prepare.js +762 -0
  41. package/dist/extensions/agent-browser/lib/orchestration/browser-run/process-output.js +491 -0
  42. package/dist/extensions/agent-browser/lib/orchestration/browser-run/prompt-guards.js +40 -0
  43. package/dist/extensions/agent-browser/lib/orchestration/browser-run/session-artifacts.js +5 -0
  44. package/dist/extensions/agent-browser/lib/orchestration/browser-run/session-state.js +731 -0
  45. package/dist/extensions/agent-browser/lib/orchestration/browser-run/types.js +1 -0
  46. package/dist/extensions/agent-browser/lib/orchestration/electron-host/index.js +718 -0
  47. package/dist/extensions/agent-browser/lib/orchestration/input-plan.js +247 -0
  48. package/dist/extensions/agent-browser/lib/orchestration/output-file.js +68 -0
  49. package/{extensions/agent-browser/lib/parsing.ts → dist/extensions/agent-browser/lib/parsing.js} +12 -11
  50. package/dist/extensions/agent-browser/lib/pi-tool-rendering.js +241 -0
  51. package/dist/extensions/agent-browser/lib/playbook.js +121 -0
  52. package/dist/extensions/agent-browser/lib/process.js +448 -0
  53. package/dist/extensions/agent-browser/lib/prompt-policy.js +91 -0
  54. package/dist/extensions/agent-browser/lib/results/action-recommendations.js +220 -0
  55. package/dist/extensions/agent-browser/lib/results/artifact-manifest.js +111 -0
  56. package/{extensions/agent-browser/lib/results/artifact-state.ts → dist/extensions/agent-browser/lib/results/artifact-state.js} +4 -8
  57. package/dist/extensions/agent-browser/lib/results/categories.js +76 -0
  58. package/dist/extensions/agent-browser/lib/results/confirmation.js +63 -0
  59. package/dist/extensions/agent-browser/lib/results/contracts.js +8 -0
  60. package/dist/extensions/agent-browser/lib/results/editable-ref-evidence.js +74 -0
  61. package/dist/extensions/agent-browser/lib/results/envelope.js +166 -0
  62. package/dist/extensions/agent-browser/lib/results/network-routes.js +92 -0
  63. package/dist/extensions/agent-browser/lib/results/network.js +73 -0
  64. package/dist/extensions/agent-browser/lib/results/next-actions.js +72 -0
  65. package/dist/extensions/agent-browser/lib/results/presentation/artifacts.js +515 -0
  66. package/dist/extensions/agent-browser/lib/results/presentation/batch.js +397 -0
  67. package/dist/extensions/agent-browser/lib/results/presentation/browser-profile-recovery.js +55 -0
  68. package/dist/extensions/agent-browser/lib/results/presentation/common.js +46 -0
  69. package/dist/extensions/agent-browser/lib/results/presentation/content.js +24 -0
  70. package/dist/extensions/agent-browser/lib/results/presentation/diagnostics.js +960 -0
  71. package/dist/extensions/agent-browser/lib/results/presentation/errors.js +205 -0
  72. package/dist/extensions/agent-browser/lib/results/presentation/large-output.js +134 -0
  73. package/dist/extensions/agent-browser/lib/results/presentation/navigation.js +159 -0
  74. package/dist/extensions/agent-browser/lib/results/presentation/registry.js +216 -0
  75. package/dist/extensions/agent-browser/lib/results/presentation/semantic-action.js +104 -0
  76. package/dist/extensions/agent-browser/lib/results/presentation/skills.js +152 -0
  77. package/dist/extensions/agent-browser/lib/results/presentation.js +177 -0
  78. package/dist/extensions/agent-browser/lib/results/recovery-actions.js +107 -0
  79. package/dist/extensions/agent-browser/lib/results/recovery-next-actions.js +50 -0
  80. package/dist/extensions/agent-browser/lib/results/selector-recovery.js +225 -0
  81. package/{extensions/agent-browser/lib/results/shared.ts → dist/extensions/agent-browser/lib/results/shared.js} +0 -1
  82. package/dist/extensions/agent-browser/lib/results/snapshot-high-value-controls.js +208 -0
  83. package/dist/extensions/agent-browser/lib/results/snapshot-refs.js +78 -0
  84. package/dist/extensions/agent-browser/lib/results/snapshot-segments.js +331 -0
  85. package/dist/extensions/agent-browser/lib/results/snapshot-spill.js +40 -0
  86. package/dist/extensions/agent-browser/lib/results/snapshot.js +264 -0
  87. package/dist/extensions/agent-browser/lib/results/text.js +40 -0
  88. package/{extensions/agent-browser/lib/results.ts → dist/extensions/agent-browser/lib/results.js} +2 -32
  89. package/dist/extensions/agent-browser/lib/runtime.js +816 -0
  90. package/dist/extensions/agent-browser/lib/session-page-state.js +411 -0
  91. package/dist/extensions/agent-browser/lib/string-enum-schema.js +13 -0
  92. package/dist/extensions/agent-browser/lib/temp.js +498 -0
  93. package/dist/extensions/agent-browser/lib/web-search.js +562 -0
  94. package/docs/RELEASE.md +22 -11
  95. package/docs/SUPPORT_MATRIX.md +4 -3
  96. package/package.json +9 -5
  97. package/scripts/config.mjs +8 -2
  98. package/scripts/doctor.mjs +8 -7
  99. package/extensions/agent-browser/index.ts +0 -961
  100. package/extensions/agent-browser/lib/argv-descriptor.ts +0 -90
  101. package/extensions/agent-browser/lib/argv-grammar.ts +0 -128
  102. package/extensions/agent-browser/lib/bash-guard.ts +0 -205
  103. package/extensions/agent-browser/lib/command-policy.ts +0 -71
  104. package/extensions/agent-browser/lib/command-taxonomy.ts +0 -336
  105. package/extensions/agent-browser/lib/config-policy.js +0 -690
  106. package/extensions/agent-browser/lib/config.ts +0 -211
  107. package/extensions/agent-browser/lib/electron/cdp.ts +0 -69
  108. package/extensions/agent-browser/lib/electron/cleanup.ts +0 -235
  109. package/extensions/agent-browser/lib/electron/discovery.ts +0 -710
  110. package/extensions/agent-browser/lib/electron/launch.ts +0 -499
  111. package/extensions/agent-browser/lib/executable-path.ts +0 -19
  112. package/extensions/agent-browser/lib/fs-utils.ts +0 -18
  113. package/extensions/agent-browser/lib/input-modes/electron.ts +0 -170
  114. package/extensions/agent-browser/lib/input-modes/job.ts +0 -527
  115. package/extensions/agent-browser/lib/input-modes/lookups.ts +0 -447
  116. package/extensions/agent-browser/lib/input-modes/params.ts +0 -205
  117. package/extensions/agent-browser/lib/input-modes/semantic-action.ts +0 -127
  118. package/extensions/agent-browser/lib/input-modes/shared.ts +0 -46
  119. package/extensions/agent-browser/lib/input-modes/types.ts +0 -225
  120. package/extensions/agent-browser/lib/input-modes.ts +0 -45
  121. package/extensions/agent-browser/lib/json-schema.ts +0 -73
  122. package/extensions/agent-browser/lib/launch-scoped-flags.ts +0 -67
  123. package/extensions/agent-browser/lib/navigation-policy.ts +0 -95
  124. package/extensions/agent-browser/lib/orchestration/batch-stdin.ts +0 -65
  125. package/extensions/agent-browser/lib/orchestration/browser-run/artifact-paths.ts +0 -44
  126. package/extensions/agent-browser/lib/orchestration/browser-run/click-dispatch.ts +0 -280
  127. package/extensions/agent-browser/lib/orchestration/browser-run/diagnostics.ts +0 -914
  128. package/extensions/agent-browser/lib/orchestration/browser-run/final-result.ts +0 -521
  129. package/extensions/agent-browser/lib/orchestration/browser-run/index.ts +0 -53
  130. package/extensions/agent-browser/lib/orchestration/browser-run/prepare/direct-anchor-download.ts +0 -158
  131. package/extensions/agent-browser/lib/orchestration/browser-run/prepare/network-page-filter.ts +0 -116
  132. package/extensions/agent-browser/lib/orchestration/browser-run/prepare/scroll-shims.ts +0 -147
  133. package/extensions/agent-browser/lib/orchestration/browser-run/prepare/snapshot-filter.ts +0 -183
  134. package/extensions/agent-browser/lib/orchestration/browser-run/prepare/wait-timeouts.ts +0 -58
  135. package/extensions/agent-browser/lib/orchestration/browser-run/prepare.ts +0 -847
  136. package/extensions/agent-browser/lib/orchestration/browser-run/process-output.ts +0 -559
  137. package/extensions/agent-browser/lib/orchestration/browser-run/prompt-guards.ts +0 -47
  138. package/extensions/agent-browser/lib/orchestration/browser-run/session-artifacts.ts +0 -8
  139. package/extensions/agent-browser/lib/orchestration/browser-run/session-state.ts +0 -868
  140. package/extensions/agent-browser/lib/orchestration/browser-run/types.ts +0 -565
  141. package/extensions/agent-browser/lib/orchestration/electron-host/index.ts +0 -855
  142. package/extensions/agent-browser/lib/orchestration/input-plan.ts +0 -375
  143. package/extensions/agent-browser/lib/orchestration/output-file.ts +0 -86
  144. package/extensions/agent-browser/lib/pi-tool-rendering.ts +0 -267
  145. package/extensions/agent-browser/lib/playbook.ts +0 -142
  146. package/extensions/agent-browser/lib/process.ts +0 -516
  147. package/extensions/agent-browser/lib/prompt-policy.ts +0 -105
  148. package/extensions/agent-browser/lib/results/action-recommendations.ts +0 -264
  149. package/extensions/agent-browser/lib/results/artifact-manifest.ts +0 -111
  150. package/extensions/agent-browser/lib/results/categories.ts +0 -106
  151. package/extensions/agent-browser/lib/results/confirmation.ts +0 -76
  152. package/extensions/agent-browser/lib/results/contracts.ts +0 -241
  153. package/extensions/agent-browser/lib/results/editable-ref-evidence.ts +0 -72
  154. package/extensions/agent-browser/lib/results/envelope.ts +0 -195
  155. package/extensions/agent-browser/lib/results/network-routes.ts +0 -83
  156. package/extensions/agent-browser/lib/results/network.ts +0 -78
  157. package/extensions/agent-browser/lib/results/next-actions.ts +0 -117
  158. package/extensions/agent-browser/lib/results/presentation/artifacts.ts +0 -588
  159. package/extensions/agent-browser/lib/results/presentation/batch.ts +0 -450
  160. package/extensions/agent-browser/lib/results/presentation/browser-profile-recovery.ts +0 -67
  161. package/extensions/agent-browser/lib/results/presentation/common.ts +0 -53
  162. package/extensions/agent-browser/lib/results/presentation/content.ts +0 -36
  163. package/extensions/agent-browser/lib/results/presentation/diagnostics.ts +0 -923
  164. package/extensions/agent-browser/lib/results/presentation/errors.ts +0 -227
  165. package/extensions/agent-browser/lib/results/presentation/large-output.ts +0 -182
  166. package/extensions/agent-browser/lib/results/presentation/navigation.ts +0 -184
  167. package/extensions/agent-browser/lib/results/presentation/registry.ts +0 -242
  168. package/extensions/agent-browser/lib/results/presentation/semantic-action.ts +0 -131
  169. package/extensions/agent-browser/lib/results/presentation/skills.ts +0 -143
  170. package/extensions/agent-browser/lib/results/presentation.ts +0 -257
  171. package/extensions/agent-browser/lib/results/recovery-actions.ts +0 -139
  172. package/extensions/agent-browser/lib/results/recovery-next-actions.ts +0 -71
  173. package/extensions/agent-browser/lib/results/selector-recovery.ts +0 -320
  174. package/extensions/agent-browser/lib/results/snapshot-high-value-controls.ts +0 -273
  175. package/extensions/agent-browser/lib/results/snapshot-refs.ts +0 -100
  176. package/extensions/agent-browser/lib/results/snapshot-segments.ts +0 -366
  177. package/extensions/agent-browser/lib/results/snapshot-spill.ts +0 -63
  178. package/extensions/agent-browser/lib/results/snapshot.ts +0 -329
  179. package/extensions/agent-browser/lib/results/text.ts +0 -40
  180. package/extensions/agent-browser/lib/runtime.ts +0 -988
  181. package/extensions/agent-browser/lib/session-page-state.ts +0 -512
  182. package/extensions/agent-browser/lib/string-enum-schema.ts +0 -20
  183. package/extensions/agent-browser/lib/temp.ts +0 -577
  184. package/extensions/agent-browser/lib/web-search.ts +0 -728
  185. /package/{extensions/agent-browser/lib/orchestration/browser-run.ts → dist/extensions/agent-browser/lib/orchestration/browser-run.js} +0 -0
@@ -1,242 +0,0 @@
1
- import type { CompiledAgentBrowserSemanticAction } from "../../input-modes/types.js";
2
- import { isRecord } from "../../parsing.js";
3
- import type { CommandInfo } from "../../runtime.js";
4
- import { detectConfirmationRequired, type ConfirmationRequiredPresentation } from "../confirmation.js";
5
- import { formatRawSnapshotText, formatSnapshotSummary } from "../snapshot.js";
6
- import { redactModelFacingText, stringifyModelFacing } from "./common.js";
7
- import { formatDiagnosticSummary, formatDiagnosticText, formatProfilesText, getStreamSummary, getTabSummary } from "./diagnostics.js";
8
- import { getScreenshotSummary } from "./artifacts.js";
9
- import { formatSkillsText } from "./skills.js";
10
- import {
11
- formatExtractionSummary,
12
- formatExtractionText,
13
- formatNavigationActionResult,
14
- formatNavigationSummary,
15
- getNavigationSummary,
16
- isNavigationObservableCommand,
17
- } from "./navigation.js";
18
- import {
19
- formatSemanticActionPresentationSummary,
20
- formatSemanticActionPresentationText,
21
- resolvePresentationCommandInfo,
22
- } from "./semantic-action.js";
23
-
24
- function getPageSummary(data: Record<string, unknown>): string | undefined {
25
- const title = typeof data.title === "string" ? data.title : undefined;
26
- const url = typeof data.url === "string" ? data.url : undefined;
27
- if (!title && !url) return undefined;
28
- if (title && url) return `${title}\n${url}`;
29
- return title ?? url;
30
- }
31
-
32
- function formatConfirmationRequiredSummary(confirmation: ConfirmationRequiredPresentation): string {
33
- return `Confirmation required: ${confirmation.id}`;
34
- }
35
-
36
- const VITALS_METRICS = ["lcp", "fcp", "ttfb", "inp", "cls"] as const;
37
-
38
- function coerceVitalsMetricValue(value: unknown): number | undefined {
39
- if (typeof value === "number" && Number.isFinite(value)) return value;
40
- if (isRecord(value)) {
41
- for (const nestedKey of ["value", "duration", "startTime", "score"] as const) {
42
- const nestedValue = value[nestedKey];
43
- if (typeof nestedValue === "number" && Number.isFinite(nestedValue)) return nestedValue;
44
- }
45
- }
46
- return undefined;
47
- }
48
-
49
- function getVitalsMetric(data: Record<string, unknown>, key: string): number | undefined {
50
- const metrics = isRecord(data.metrics) ? data.metrics : undefined;
51
- return coerceVitalsMetricValue(data[key] ?? data[key.toUpperCase()] ?? metrics?.[key] ?? metrics?.[key.toUpperCase()]);
52
- }
53
-
54
- function formatVitalsMetric(key: string, value: number): string {
55
- return key === "cls" ? `${key.toUpperCase()}: ${value}` : `${key.toUpperCase()}: ${Math.round(value)}ms`;
56
- }
57
-
58
- function getVitalsMetrics(data: Record<string, unknown>): string[] {
59
- return VITALS_METRICS.flatMap((key) => {
60
- const value = getVitalsMetric(data, key);
61
- return value === undefined ? [] : [formatVitalsMetric(key, value)];
62
- });
63
- }
64
-
65
- function getVitalsUnavailableReason(data: Record<string, unknown>): string {
66
- for (const key of ["reason", "message", "error", "status"] as const) {
67
- const value = data[key];
68
- if (typeof value === "string" && value.trim().length > 0) return redactModelFacingText(value.trim());
69
- }
70
- return "No Core Web Vitals metric fields were present in the upstream result.";
71
- }
72
-
73
- function formatVitalsText(data: Record<string, unknown>): string {
74
- const url = typeof data.url === "string" && data.url.trim().length > 0 ? redactModelFacingText(data.url.trim()) : undefined;
75
- const metrics = getVitalsMetrics(data);
76
- const lines = [url ? `Vitals for ${url}` : "Vitals result"];
77
- if (metrics.length > 0) lines.push(...metrics.map((metric) => `- ${metric}`));
78
- else lines.push(`Metrics unavailable: ${getVitalsUnavailableReason(data)}`);
79
- return lines.join("\n");
80
- }
81
-
82
- function formatVitalsSummary(data: Record<string, unknown>): string | undefined {
83
- const metrics = getVitalsMetrics(data);
84
- if (metrics.length > 0) return `Vitals: ${metrics.join(", ")}`;
85
- return "Vitals: metrics unavailable";
86
- }
87
-
88
- function formatConfirmationRequiredText(confirmation: ConfirmationRequiredPresentation): string {
89
- const lines = [
90
- "Confirmation required.",
91
- `Pending confirmation id: ${confirmation.id}`,
92
- ];
93
- if (confirmation.actionText) lines.push(`Action: ${confirmation.actionText}`);
94
- lines.push(
95
- "",
96
- "Next steps:",
97
- `- Approve: { "args": ["confirm", "${confirmation.id}"] }`,
98
- `- Deny: { "args": ["deny", "${confirmation.id}"] }`,
99
- );
100
- return lines.join("\n");
101
- }
102
-
103
- interface CommandPresenter {
104
- summary?: (commandInfo: CommandInfo, data: unknown) => string | undefined;
105
- text?: (commandInfo: CommandInfo, data: unknown) => string | undefined;
106
- }
107
-
108
- const COMMAND_PRESENTERS: Record<string, CommandPresenter> = {
109
- profiles: {
110
- summary: (_commandInfo, data) => Array.isArray(data) ? `Chrome profiles: ${data.length}` : undefined,
111
- text: (_commandInfo, data) => Array.isArray(data) ? formatProfilesText(data, "Chrome profiles") : undefined,
112
- },
113
- screenshot: {
114
- summary: (_commandInfo, data) => isRecord(data) && typeof data.path === "string" ? `Screenshot saved: ${data.path}` : undefined,
115
- text: (_commandInfo, data) => isRecord(data) ? getScreenshotSummary(data) : undefined,
116
- },
117
- skills: {
118
- summary: (commandInfo, data) => {
119
- if (Array.isArray(data) && commandInfo.subcommand === "list") return `agent-browser skills: ${data.length}`;
120
- if (commandInfo.subcommand === "get") return "agent-browser skill loaded";
121
- if (commandInfo.subcommand === "path") return "agent-browser skill path";
122
- return undefined;
123
- },
124
- text: formatSkillsText,
125
- },
126
- snapshot: {
127
- summary: (_commandInfo, data) => isRecord(data) ? formatSnapshotSummary(data) : undefined,
128
- text: (_commandInfo, data) => isRecord(data) ? formatRawSnapshotText(data) : undefined,
129
- },
130
- stream: {
131
- summary: (commandInfo, data) => {
132
- if (!isRecord(data) || commandInfo.subcommand !== "status") return undefined;
133
- const port = typeof data.port === "number" ? ` on port ${data.port}` : "";
134
- return `Stream ${data.enabled === true ? "enabled" : "disabled"}${port}`;
135
- },
136
- text: (commandInfo, data) => isRecord(data) && commandInfo.subcommand === "status" ? getStreamSummary(data) : undefined,
137
- },
138
- tab: {
139
- summary: (_commandInfo, data) => isRecord(data) && Array.isArray(data.tabs) ? `Tabs: ${data.tabs.length}` : undefined,
140
- text: (_commandInfo, data) => isRecord(data) ? getTabSummary(data) : undefined,
141
- },
142
- vitals: {
143
- summary: (_commandInfo, data) => isRecord(data) ? formatVitalsSummary(data) : undefined,
144
- text: (_commandInfo, data) => isRecord(data) ? formatVitalsText(data) : undefined,
145
- },
146
- "web-vitals": {
147
- summary: (_commandInfo, data) => isRecord(data) ? formatVitalsSummary(data) : undefined,
148
- text: (_commandInfo, data) => isRecord(data) ? formatVitalsText(data) : undefined,
149
- },
150
- };
151
-
152
- function formatBatchSummary(data: unknown): string | undefined {
153
- if (!Array.isArray(data)) return undefined;
154
- const successCount = data.filter((item) => isRecord(item) && item.success !== false).length;
155
- return successCount === data.length
156
- ? `Batch: ${successCount}/${data.length} succeeded`
157
- : `Batch failed: ${successCount}/${data.length} succeeded`;
158
- }
159
-
160
- export function formatPresentationSummary(
161
- commandInfo: CommandInfo,
162
- data: unknown,
163
- compiledSemanticAction?: CompiledAgentBrowserSemanticAction,
164
- ): string {
165
- const confirmationRequired = detectConfirmationRequired(data);
166
- if (confirmationRequired) return formatConfirmationRequiredSummary(confirmationRequired);
167
-
168
- const presentationCommandInfo = resolvePresentationCommandInfo(commandInfo, compiledSemanticAction);
169
-
170
- if (commandInfo.command === "batch") {
171
- const batchSummary = formatBatchSummary(data);
172
- if (batchSummary) return batchSummary;
173
- }
174
-
175
- if (isRecord(data)) {
176
- if (compiledSemanticAction) {
177
- const semanticSummary = formatSemanticActionPresentationSummary(compiledSemanticAction, data);
178
- if (semanticSummary) return semanticSummary;
179
- }
180
- const navigationSummary = getNavigationSummary(data);
181
- if (navigationSummary && isNavigationObservableCommand(presentationCommandInfo.command)) {
182
- const navigationText = formatNavigationSummary(navigationSummary);
183
- if (navigationText) {
184
- return `${presentationCommandInfo.command ?? "navigation"} → ${navigationText.split("\n", 1)[0] ?? navigationText}`;
185
- }
186
- }
187
- }
188
-
189
- const presenterSummary = commandInfo.command ? COMMAND_PRESENTERS[commandInfo.command]?.summary?.(commandInfo, data) : undefined;
190
- if (presenterSummary) return presenterSummary;
191
-
192
- if (isRecord(data)) {
193
- const diagnosticSummary = formatDiagnosticSummary(commandInfo, data);
194
- if (diagnosticSummary) return diagnosticSummary;
195
- const extractionSummary = formatExtractionSummary(commandInfo, data);
196
- if (extractionSummary) return extractionSummary;
197
- const pageSummary = getPageSummary(data);
198
- if (pageSummary) return pageSummary.split("\n", 1)[0] ?? "agent-browser result";
199
- }
200
-
201
- if (typeof data === "string" && data.length > 0) return data.split("\n", 1)[0] ?? data;
202
- return `${presentationCommandInfo.command ?? commandInfo.command ?? "agent-browser"} completed`;
203
- }
204
-
205
- export function formatPresentationContentText(
206
- commandInfo: CommandInfo,
207
- data: unknown,
208
- compiledSemanticAction?: CompiledAgentBrowserSemanticAction,
209
- ): string {
210
- const confirmationRequired = detectConfirmationRequired(data);
211
- if (confirmationRequired) return formatConfirmationRequiredText(confirmationRequired);
212
-
213
- const presenterText = commandInfo.command ? COMMAND_PRESENTERS[commandInfo.command]?.text?.(commandInfo, data) : undefined;
214
- if (presenterText) return presenterText;
215
-
216
- if (typeof data === "string") return redactModelFacingText(data);
217
- if (typeof data === "number" || typeof data === "boolean") return String(data);
218
- if (!isRecord(data)) return stringifyModelFacing(data);
219
-
220
- if (compiledSemanticAction) {
221
- const semanticText = formatSemanticActionPresentationText(compiledSemanticAction, data);
222
- if (semanticText) return semanticText;
223
- }
224
-
225
- const presentationCommandInfo = resolvePresentationCommandInfo(commandInfo, compiledSemanticAction);
226
- const navigationSummary = getNavigationSummary(data);
227
- if (navigationSummary && isNavigationObservableCommand(presentationCommandInfo.command)) {
228
- const navigationText = formatNavigationSummary(navigationSummary);
229
- if (navigationText) {
230
- const actionText = formatNavigationActionResult(data);
231
- return actionText ? `${actionText}\n\nCurrent page:\n${navigationText}` : `Current page:\n${navigationText}`;
232
- }
233
- }
234
-
235
- const extractionText = formatExtractionText(commandInfo, data);
236
- if (extractionText) return extractionText;
237
- const diagnosticText = formatDiagnosticText(commandInfo, data);
238
- if (diagnosticText) return diagnosticText;
239
- const pageSummary = getPageSummary(data);
240
- if (pageSummary) return redactModelFacingText(pageSummary);
241
- return stringifyModelFacing(data);
242
- }
@@ -1,131 +0,0 @@
1
- /**
2
- * Purpose: Map successful semanticAction results to the same presentation signals as direct ref commands.
3
- * Responsibilities: Resolve presentation command names, compact action prose, and navigation-summary probe gates.
4
- * Scope: semanticAction success presentation only.
5
- */
6
-
7
- import {
8
- getCompiledSemanticActionCommandIndex,
9
- isCompiledSemanticActionFindCommand,
10
- } from "../../input-modes/semantic-action.js";
11
- import type { CompiledAgentBrowserSemanticAction } from "../../input-modes/types.js";
12
- import { isRecord } from "../../parsing.js";
13
- import type { CommandInfo } from "../../runtime.js";
14
- import {
15
- formatNavigationSummary,
16
- getNavigationSummary,
17
- isNavigationObservableCommand,
18
- } from "./navigation.js";
19
- import { redactModelFacingText } from "./common.js";
20
-
21
- const SEMANTIC_NAVIGATION_PROBE_ACTIONS = new Set(["check", "click"]);
22
-
23
- const SEMANTIC_PRESENTATION_ACTIONS = new Set(["check", "click", "fill", "select"]);
24
-
25
- function getPageSummary(data: Record<string, unknown>): string | undefined {
26
- const title = typeof data.title === "string" ? data.title : undefined;
27
- const url = typeof data.url === "string" ? data.url : undefined;
28
- if (!title && !url) return undefined;
29
- if (title && url) return `${title}\n${url}`;
30
- return title ?? url;
31
- }
32
-
33
- function formatSemanticActionTarget(compiled: CompiledAgentBrowserSemanticAction): string {
34
- if (compiled.action === "select") {
35
- const selector = compiled.selector ?? "selector";
36
- const values = compiled.values?.length ? compiled.values.join(", ") : "";
37
- return values ? `${selector} → ${values}` : selector;
38
- }
39
- const commandIndex = getCompiledSemanticActionCommandIndex(compiled);
40
- const locator = compiled.locator ?? compiled.args[commandIndex + 1] ?? "locator";
41
- const locatorValue = compiled.args[commandIndex + 2];
42
- const nameIndex = compiled.args.indexOf("--name");
43
- const name = nameIndex >= 0 ? compiled.args[nameIndex + 1] : undefined;
44
- const quotedValue = JSON.stringify(locatorValue ?? "");
45
- const target = `${locator} ${quotedValue}`;
46
- return name ? `${target} (name ${JSON.stringify(name)})` : target;
47
- }
48
-
49
- export function formatSemanticActionCompactLine(compiled: CompiledAgentBrowserSemanticAction): string {
50
- const target = formatSemanticActionTarget(compiled);
51
- switch (compiled.action) {
52
- case "click":
53
- return `Clicked: ${target}`;
54
- case "fill":
55
- return `Filled: ${target}`;
56
- case "check":
57
- return `Checked: ${target}`;
58
- case "select":
59
- return `Selected: ${target}`;
60
- default:
61
- return `${compiled.action}: ${target}`;
62
- }
63
- }
64
-
65
- export function resolveSemanticPresentationCommand(
66
- compiled: CompiledAgentBrowserSemanticAction | undefined,
67
- ): string | undefined {
68
- if (!compiled || !SEMANTIC_PRESENTATION_ACTIONS.has(compiled.action)) return undefined;
69
- if (compiled.action === "select") return "select";
70
- if (isCompiledSemanticActionFindCommand(compiled)) return compiled.action;
71
- return undefined;
72
- }
73
-
74
- export function resolvePresentationCommandInfo(
75
- commandInfo: CommandInfo,
76
- compiledSemanticAction?: CompiledAgentBrowserSemanticAction,
77
- ): CommandInfo {
78
- const presentationCommand = resolveSemanticPresentationCommand(compiledSemanticAction);
79
- if (!presentationCommand) return commandInfo;
80
- return { ...commandInfo, command: presentationCommand };
81
- }
82
-
83
- export function shouldCaptureSemanticActionNavigationSummary(
84
- compiled: CompiledAgentBrowserSemanticAction | undefined,
85
- data: unknown,
86
- ): boolean {
87
- if (!compiled || !SEMANTIC_NAVIGATION_PROBE_ACTIONS.has(compiled.action)) return false;
88
- if (!isCompiledSemanticActionFindCommand(compiled)) return false;
89
- return !isRecord(data) || (typeof data.title !== "string" && typeof data.url !== "string");
90
- }
91
-
92
- export function formatSemanticActionPresentationText(
93
- compiled: CompiledAgentBrowserSemanticAction,
94
- data: Record<string, unknown>,
95
- ): string | undefined {
96
- const presentationCommand = resolveSemanticPresentationCommand(compiled);
97
- if (!presentationCommand) return undefined;
98
-
99
- const actionLine = formatSemanticActionCompactLine(compiled);
100
- const navigationSummary = getNavigationSummary(data);
101
- if (navigationSummary && isNavigationObservableCommand(presentationCommand)) {
102
- const navigationText = formatNavigationSummary(navigationSummary);
103
- if (navigationText) return `${actionLine}\n\nCurrent page:\n${navigationText}`;
104
- }
105
-
106
- const pageSummary = getPageSummary(data);
107
- if (pageSummary) return `${actionLine}\n\nCurrent page:\n${redactModelFacingText(pageSummary)}`;
108
-
109
- return actionLine;
110
- }
111
-
112
- export function formatSemanticActionPresentationSummary(
113
- compiled: CompiledAgentBrowserSemanticAction,
114
- data: Record<string, unknown>,
115
- ): string | undefined {
116
- const presentationCommand = resolveSemanticPresentationCommand(compiled);
117
- if (!presentationCommand) return undefined;
118
-
119
- const navigationSummary = getNavigationSummary(data);
120
- if (navigationSummary && isNavigationObservableCommand(presentationCommand)) {
121
- const navigationText = formatNavigationSummary(navigationSummary);
122
- if (navigationText) {
123
- return `${presentationCommand} → ${navigationText.split("\n", 1)[0] ?? navigationText}`;
124
- }
125
- }
126
-
127
- const pageSummary = getPageSummary(data);
128
- if (pageSummary) return `${presentationCommand} → ${pageSummary.split("\n", 1)[0] ?? pageSummary}`;
129
-
130
- return `${presentationCommand} → ${formatSemanticActionTarget(compiled)}`;
131
- }
@@ -1,143 +0,0 @@
1
- /**
2
- * Purpose: Render upstream agent-browser skills output as native pi tool guidance.
3
- * Responsibilities: Format skills list/path/get results and translate agent-browser shell snippets to agent_browser tool calls.
4
- * Scope: Skills command presentation only.
5
- */
6
-
7
- import { isRecord } from "../../parsing.js";
8
- import type { CommandInfo } from "../../runtime.js";
9
- import { getStringField, redactModelFacingText, stringifyModelFacing } from "./common.js";
10
-
11
- function formatSkillsListText(skills: unknown[]): string {
12
- if (skills.length === 0) return "No agent-browser skills found.";
13
- return skills
14
- .map((item, index) => {
15
- if (!isRecord(item)) return `${index + 1}. ${stringifyModelFacing(item)}`;
16
- const name = redactModelFacingText(getStringField(item, "name") ?? `(skill ${index + 1})`);
17
- const description = getStringField(item, "description");
18
- return description ? `${index + 1}. ${name} — ${redactModelFacingText(description)}` : `${index + 1}. ${name}`;
19
- })
20
- .join("\n");
21
- }
22
-
23
- function getSkillContent(data: unknown): string | undefined {
24
- if (typeof data === "string") return data;
25
- if (isRecord(data) && typeof data.content === "string") return data.content;
26
- if (!Array.isArray(data)) return undefined;
27
- const content = data.flatMap((item) => (isRecord(item) && typeof item.content === "string" ? [item.content] : []));
28
- return content.length > 0 ? content.join("\n\n") : undefined;
29
- }
30
-
31
- function splitShellWords(input: string): string[] | undefined {
32
- const words: string[] = [];
33
- let current = "";
34
- let quote: 'single' | 'double' | undefined;
35
- for (let index = 0; index < input.length; index += 1) {
36
- const char = input[index];
37
- if (quote === "single") {
38
- if (char === "'") quote = undefined;
39
- else current += char;
40
- continue;
41
- }
42
- if (quote === "double") {
43
- if (char === '"') quote = undefined;
44
- else if (char === "\\" && index + 1 < input.length) {
45
- index += 1;
46
- current += input[index];
47
- } else current += char;
48
- continue;
49
- }
50
- if (char === "'") {
51
- quote = "single";
52
- continue;
53
- }
54
- if (char === '"') {
55
- quote = "double";
56
- continue;
57
- }
58
- if (char === "\\" && index + 1 < input.length) {
59
- index += 1;
60
- current += input[index];
61
- continue;
62
- }
63
- if (char === "#" && current.length === 0) {
64
- break;
65
- }
66
- if (/\s/.test(char)) {
67
- if (current.length > 0) {
68
- words.push(current);
69
- current = "";
70
- }
71
- continue;
72
- }
73
- current += char;
74
- }
75
- if (quote) return undefined;
76
- if (current.length > 0) words.push(current);
77
- return words;
78
- }
79
-
80
- function formatNativeAgentBrowserCall(args: string[], stdin?: string): string {
81
- return stdin === undefined
82
- ? `agent_browser { "args": ${JSON.stringify(args)} }`
83
- : `agent_browser { "args": ${JSON.stringify(args)}, "stdin": ${JSON.stringify(stdin)} }`;
84
- }
85
-
86
- function formatNativeSkillContent(content: string): string {
87
- const lines = content.replace(/^allowed-tools:.*agent-browser.*\n?/gim, "").replace(/^```bash\s*$/gim, "```text").split("\n");
88
- const output: string[] = [];
89
- for (let index = 0; index < lines.length; index += 1) {
90
- const line = lines[index];
91
- const commandMatch = /^(\s*)agent-browser\s+(.+?)\s*$/.exec(line);
92
- if (!commandMatch) {
93
- output.push(line);
94
- continue;
95
- }
96
- const indent = commandMatch[1];
97
- const rawArgsText = commandMatch[2];
98
- const heredocMatch = /^(.*?)\s+(<<-?)['"]?([A-Za-z_][A-Za-z0-9_]*)['"]?\s*$/.exec(rawArgsText);
99
- const argsText = heredocMatch?.[1] ?? rawArgsText;
100
- const args = splitShellWords(argsText);
101
- if (!args || args.length === 0) {
102
- output.push(line);
103
- continue;
104
- }
105
- if (!heredocMatch) {
106
- output.push(`${indent}${formatNativeAgentBrowserCall(args)}`);
107
- continue;
108
- }
109
- const stripsLeadingTabs = heredocMatch[2] === "<<-";
110
- const delimiter = heredocMatch[3];
111
- const stdinLines: string[] = [];
112
- let cursor = index + 1;
113
- while (cursor < lines.length) {
114
- const candidate = stripsLeadingTabs ? lines[cursor].replace(/^\t+/, "") : lines[cursor];
115
- if (candidate === delimiter) break;
116
- stdinLines.push(candidate);
117
- cursor += 1;
118
- }
119
- if (cursor >= lines.length) {
120
- output.push(line);
121
- continue;
122
- }
123
- output.push(`${indent}${formatNativeAgentBrowserCall(args, stdinLines.join("\n"))}`);
124
- index = cursor;
125
- }
126
- return output.join("\n");
127
- }
128
-
129
- export function formatSkillsText(commandInfo: CommandInfo, data: unknown): string | undefined {
130
- if (commandInfo.command !== "skills") return undefined;
131
- if (commandInfo.subcommand === "path") return typeof data === "string" ? redactModelFacingText(data) : undefined;
132
- if (commandInfo.subcommand === "list" && Array.isArray(data)) return formatSkillsListText(data);
133
- const content = getSkillContent(data);
134
- if (content) {
135
- const note = [
136
- "Pi native-tool note: upstream skill text was adapted for this native tool.",
137
- "Use args for CLI tokens and stdin only for batch, eval --stdin, or auth save --password-stdin; do not pipe heredocs through bash unless the user explicitly asks for a bash workflow.",
138
- ].join("\n");
139
- return `${note}\n\n${redactModelFacingText(formatNativeSkillContent(content))}`;
140
- }
141
- if (typeof data === "string") return redactModelFacingText(formatNativeSkillContent(data));
142
- return undefined;
143
- }