chrome-relay 0.5.9 → 0.5.11
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/dist/cli.js +159 -41
- package/dist/index.js +1 -1
- package/dist/native-host.js +1 -1
- package/package.json +1 -1
package/dist/cli.js
CHANGED
|
@@ -1,50 +1,142 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
+
var __defProp = Object.defineProperty;
|
|
3
|
+
var __getOwnPropNames = Object.getOwnPropertyNames;
|
|
4
|
+
var __esm = (fn, res) => function __init() {
|
|
5
|
+
return fn && (res = (0, fn[__getOwnPropNames(fn)[0]])(fn = 0)), res;
|
|
6
|
+
};
|
|
7
|
+
var __export = (target, all) => {
|
|
8
|
+
for (var name in all)
|
|
9
|
+
__defProp(target, name, { get: all[name], enumerable: true });
|
|
10
|
+
};
|
|
11
|
+
|
|
12
|
+
// ../protocol/dist/index.js
|
|
13
|
+
var dist_exports = {};
|
|
14
|
+
__export(dist_exports, {
|
|
15
|
+
CHROME_WEB_STORE_EXTENSION_ID: () => CHROME_WEB_STORE_EXTENSION_ID,
|
|
16
|
+
DEFAULT_EXTENSION_ID: () => DEFAULT_EXTENSION_ID,
|
|
17
|
+
DEFAULT_EXTENSION_IDS: () => DEFAULT_EXTENSION_IDS,
|
|
18
|
+
DEFAULT_HTTP_PORT: () => DEFAULT_HTTP_PORT,
|
|
19
|
+
LEGACY_DEV_EXTENSION_ID: () => LEGACY_DEV_EXTENSION_ID,
|
|
20
|
+
LOCAL_UNPACKED_EXTENSION_ID: () => LOCAL_UNPACKED_EXTENSION_ID,
|
|
21
|
+
NATIVE_HOST_NAME: () => NATIVE_HOST_NAME,
|
|
22
|
+
RelayError: () => RelayError,
|
|
23
|
+
TOOL_NAMES: () => TOOL_NAMES,
|
|
24
|
+
toBridgeError: () => toBridgeError
|
|
25
|
+
});
|
|
26
|
+
function toBridgeError(unknownErr, fallbackTool) {
|
|
27
|
+
if (unknownErr instanceof RelayError) {
|
|
28
|
+
const e = unknownErr.toBridgeError();
|
|
29
|
+
return fallbackTool && !e.tool ? { ...e, tool: fallbackTool } : e;
|
|
30
|
+
}
|
|
31
|
+
const message = unknownErr instanceof Error ? unknownErr.message : String(unknownErr);
|
|
32
|
+
return {
|
|
33
|
+
code: "internal_error",
|
|
34
|
+
message,
|
|
35
|
+
...fallbackTool ? { tool: fallbackTool } : {}
|
|
36
|
+
};
|
|
37
|
+
}
|
|
38
|
+
var NATIVE_HOST_NAME, DEFAULT_HTTP_PORT, CHROME_WEB_STORE_EXTENSION_ID, LEGACY_DEV_EXTENSION_ID, LOCAL_UNPACKED_EXTENSION_ID, DEFAULT_EXTENSION_ID, DEFAULT_EXTENSION_IDS, TOOL_NAMES, RelayError;
|
|
39
|
+
var init_dist = __esm({
|
|
40
|
+
"../protocol/dist/index.js"() {
|
|
41
|
+
"use strict";
|
|
42
|
+
NATIVE_HOST_NAME = "dev.chrome_relay.native_host";
|
|
43
|
+
DEFAULT_HTTP_PORT = 12122;
|
|
44
|
+
CHROME_WEB_STORE_EXTENSION_ID = "cpdiapbifblhlcpnmlmfpgfjlacebokb";
|
|
45
|
+
LEGACY_DEV_EXTENSION_ID = "cdmmkpadhnpcfjljhgpdnnljhjafmhop";
|
|
46
|
+
LOCAL_UNPACKED_EXTENSION_ID = "cleiodnaklknhhfopegimjelfibjmbkc";
|
|
47
|
+
DEFAULT_EXTENSION_ID = CHROME_WEB_STORE_EXTENSION_ID;
|
|
48
|
+
DEFAULT_EXTENSION_IDS = [
|
|
49
|
+
CHROME_WEB_STORE_EXTENSION_ID,
|
|
50
|
+
LEGACY_DEV_EXTENSION_ID,
|
|
51
|
+
LOCAL_UNPACKED_EXTENSION_ID
|
|
52
|
+
];
|
|
53
|
+
TOOL_NAMES = {
|
|
54
|
+
GET_WINDOWS_AND_TABS: "get_windows_and_tabs",
|
|
55
|
+
NAVIGATE: "chrome_navigate",
|
|
56
|
+
SWITCH_TAB: "chrome_switch_tab",
|
|
57
|
+
CLOSE_TABS: "chrome_close_tabs",
|
|
58
|
+
SCREENSHOT: "chrome_screenshot",
|
|
59
|
+
READ_PAGE: "chrome_read_page",
|
|
60
|
+
CLICK: "chrome_click_element",
|
|
61
|
+
FILL: "chrome_fill_or_select",
|
|
62
|
+
KEYBOARD: "chrome_keyboard",
|
|
63
|
+
TYPE: "chrome_type",
|
|
64
|
+
EVALUATE: "chrome_evaluate",
|
|
65
|
+
// §2.2 — viewport emulation (set/preset/clear share one tool, action via args.action)
|
|
66
|
+
VIEWPORT: "chrome_viewport",
|
|
67
|
+
// chrome_self_reload — calls chrome.runtime.reload() inside the extension.
|
|
68
|
+
// Lets the dev loop refresh the extension without manually clicking reload
|
|
69
|
+
// on chrome://extensions (Chrome blocks CDP attach on chrome:// pages).
|
|
70
|
+
SELF_RELOAD: "chrome_self_reload",
|
|
71
|
+
// §2.7c — console capture. Ring-buffer per tab; actions read/clear via args.
|
|
72
|
+
CONSOLE: "chrome_console",
|
|
73
|
+
// Workspaces — named Chrome windows for parallel agent work. Single tool
|
|
74
|
+
// with action: create | list | close. Every existing tool also accepts an
|
|
75
|
+
// optional workspaceName arg that routes ops into that workspace's window.
|
|
76
|
+
// (Was "chrome_group" pre-0.4.0; renamed because "group" collides with
|
|
77
|
+
// Chrome's own tab-group UI primitive, which is now exposed separately.)
|
|
78
|
+
WORKSPACE: "chrome_workspace",
|
|
79
|
+
// Tab groups — Chrome's native colored, collapsible folder of tabs inside
|
|
80
|
+
// a single window. Single tool with action: create | list | close | add | remove.
|
|
81
|
+
// Every existing tool also accepts an optional groupName arg that routes
|
|
82
|
+
// ops to a tab inside that tab-group.
|
|
83
|
+
GROUP: "chrome_group",
|
|
84
|
+
// §2.4 — accessibility tree. ~30× smaller than DOM serialization, more
|
|
85
|
+
// semantic. click_ax pairs with it: targets by backendDOMNodeId, no CSS.
|
|
86
|
+
AX: "chrome_ax",
|
|
87
|
+
CLICK_AX: "chrome_click_ax",
|
|
88
|
+
// §2.7a — network capture. Ring-buffer per tab; actions read/clear/har/body.
|
|
89
|
+
NETWORK: "chrome_network",
|
|
90
|
+
// Hover — dispatches mouseMoved at element center (or x,y) so :hover/
|
|
91
|
+
// :focus-within styles fire before a click or screencast frame is read.
|
|
92
|
+
HOVER: "chrome_hover",
|
|
93
|
+
// Screencast — wraps CDP Page.startScreencast / stopScreencast. SW buffers
|
|
94
|
+
// base64 JPEG frames per tab between start and stop. Paint-driven (catches
|
|
95
|
+
// CSS transitions, fade-ins, focus-ring motion) — at the cost of requiring
|
|
96
|
+
// the tab to be ACTIVE (Chrome doesn't paint backgrounded tabs). See
|
|
97
|
+
// docs/recording.md for the active-tab matrix.
|
|
98
|
+
SCREENCAST: "chrome_screencast"
|
|
99
|
+
};
|
|
100
|
+
RelayError = class extends Error {
|
|
101
|
+
code;
|
|
102
|
+
tool;
|
|
103
|
+
phase;
|
|
104
|
+
details;
|
|
105
|
+
retryable;
|
|
106
|
+
constructor(spec) {
|
|
107
|
+
super(spec.message);
|
|
108
|
+
this.name = "RelayError";
|
|
109
|
+
this.code = spec.code;
|
|
110
|
+
this.tool = spec.tool;
|
|
111
|
+
this.phase = spec.phase;
|
|
112
|
+
this.details = spec.details;
|
|
113
|
+
this.retryable = spec.retryable;
|
|
114
|
+
}
|
|
115
|
+
toBridgeError() {
|
|
116
|
+
return {
|
|
117
|
+
code: this.code,
|
|
118
|
+
message: this.message,
|
|
119
|
+
...this.tool ? { tool: this.tool } : {},
|
|
120
|
+
...this.phase ? { phase: this.phase } : {},
|
|
121
|
+
...this.details ? { details: this.details } : {},
|
|
122
|
+
...this.retryable !== void 0 ? { retryable: this.retryable } : {}
|
|
123
|
+
};
|
|
124
|
+
}
|
|
125
|
+
};
|
|
126
|
+
}
|
|
127
|
+
});
|
|
2
128
|
|
|
3
129
|
// src/program.ts
|
|
4
130
|
import { Command } from "commander";
|
|
5
131
|
|
|
6
132
|
// src/index.ts
|
|
7
|
-
var CHROME_RELAY_VERSION = true ? "0.5.
|
|
133
|
+
var CHROME_RELAY_VERSION = true ? "0.5.11" : "0.0.0-dev";
|
|
8
134
|
|
|
9
|
-
//
|
|
10
|
-
|
|
11
|
-
var DEFAULT_HTTP_PORT = 12122;
|
|
12
|
-
var CHROME_WEB_STORE_EXTENSION_ID = "cpdiapbifblhlcpnmlmfpgfjlacebokb";
|
|
13
|
-
var LEGACY_DEV_EXTENSION_ID = "cdmmkpadhnpcfjljhgpdnnljhjafmhop";
|
|
14
|
-
var LOCAL_UNPACKED_EXTENSION_ID = "cleiodnaklknhhfopegimjelfibjmbkc";
|
|
15
|
-
var DEFAULT_EXTENSION_IDS = [
|
|
16
|
-
CHROME_WEB_STORE_EXTENSION_ID,
|
|
17
|
-
LEGACY_DEV_EXTENSION_ID,
|
|
18
|
-
LOCAL_UNPACKED_EXTENSION_ID
|
|
19
|
-
];
|
|
20
|
-
var RelayError = class extends Error {
|
|
21
|
-
code;
|
|
22
|
-
tool;
|
|
23
|
-
phase;
|
|
24
|
-
details;
|
|
25
|
-
retryable;
|
|
26
|
-
constructor(spec) {
|
|
27
|
-
super(spec.message);
|
|
28
|
-
this.name = "RelayError";
|
|
29
|
-
this.code = spec.code;
|
|
30
|
-
this.tool = spec.tool;
|
|
31
|
-
this.phase = spec.phase;
|
|
32
|
-
this.details = spec.details;
|
|
33
|
-
this.retryable = spec.retryable;
|
|
34
|
-
}
|
|
35
|
-
toBridgeError() {
|
|
36
|
-
return {
|
|
37
|
-
code: this.code,
|
|
38
|
-
message: this.message,
|
|
39
|
-
...this.tool ? { tool: this.tool } : {},
|
|
40
|
-
...this.phase ? { phase: this.phase } : {},
|
|
41
|
-
...this.details ? { details: this.details } : {},
|
|
42
|
-
...this.retryable !== void 0 ? { retryable: this.retryable } : {}
|
|
43
|
-
};
|
|
44
|
-
}
|
|
45
|
-
};
|
|
135
|
+
// src/commands/shared.ts
|
|
136
|
+
init_dist();
|
|
46
137
|
|
|
47
138
|
// src/client/call.ts
|
|
139
|
+
init_dist();
|
|
48
140
|
var noticePrinted = false;
|
|
49
141
|
function emitNoticeOnce(notice) {
|
|
50
142
|
if (noticePrinted) return;
|
|
@@ -162,6 +254,7 @@ async function runToolImpl(name, args) {
|
|
|
162
254
|
var runTool = runToolImpl;
|
|
163
255
|
|
|
164
256
|
// src/install/install.ts
|
|
257
|
+
init_dist();
|
|
165
258
|
import os from "os";
|
|
166
259
|
import path from "path";
|
|
167
260
|
import { chmod, mkdir, readFile, stat, writeFile } from "fs/promises";
|
|
@@ -271,6 +364,17 @@ async function runDoctor() {
|
|
|
271
364
|
|
|
272
365
|
// src/release-notes.ts
|
|
273
366
|
var RELEASE_NOTES = {
|
|
367
|
+
"0.5.11": [
|
|
368
|
+
"Tests-only: 6 new edge-case tests for `chrome-relay update`. Covers --dry-run, install failure, install-success-but-binary-version-unchanged (PATH mismatch / stale shim), install-success-but-which-fails, install-success-but-release-notes-parse-fails, and the happy path. Locks in the structured-metadata contract from 0.5.7.",
|
|
369
|
+
"Total tests now 378 (was 372)."
|
|
370
|
+
],
|
|
371
|
+
"0.5.10": [
|
|
372
|
+
"Direct /call target conflict enforcement. Third-party callers posting to /call with multiple loose target fields (tabId + workspaceName, etc.) now throw `target_conflict` instead of silently applying precedence. Matches the CLI rule the CLI itself enforced since 0.5.4.",
|
|
373
|
+
"All useful plain Error throws in extension handlers converted to RelayError(invalid_arguments). Affected tools: chrome_click_element, chrome_fill_or_select, chrome_keyboard, chrome_type, chrome_evaluate, chrome_switch_tab, chrome_close_tabs, chrome_viewport (preset name + width/height), chrome_workspace (create/close), chrome_group (create/close/add/remove), chrome_network (body without --request-id), chrome_hover (no selector or x,y), chrome_click_ax (no --node), and bbox parser. Agents can now branch on `errorDetails.code === 'invalid_arguments'` for all of these.",
|
|
374
|
+
"chrome_hover with a selector that doesn't match now throws RelayError(`element_not_found`) (was plain Error).",
|
|
375
|
+
"BEHAVIOR CHANGE \u2014 `chrome-relay screencast stop --gif/--mp4` is no longer best-effort when ffmpeg is missing. Old behavior printed 'skipping' and exited 0 (agent saw success but no GIF existed). New behavior throws `external_dependency_missing` with exit 1. Pass `--allow-missing-ffmpeg` to restore the legacy skip-with-warning behavior.",
|
|
376
|
+
"Tests: +17 in handler-strict.test.ts covering the conflict + 13 missing-arg paths. Total now 372."
|
|
377
|
+
],
|
|
274
378
|
"0.5.9": [
|
|
275
379
|
"Internal refactor (code-quality-hardening PR 7): program.ts and tools.ts split into per-domain modules. Pure code motion, no behavior change.",
|
|
276
380
|
"CLI: packages/cli/src/program.ts shrank from 1041 \u2192 75 lines. Per-domain modules now live in packages/cli/src/commands/{install-update,navigation,input,capture,sessions}.ts.",
|
|
@@ -728,7 +832,7 @@ Notes:
|
|
|
728
832
|
await run("chrome_screencast", args);
|
|
729
833
|
});
|
|
730
834
|
tabOpt(
|
|
731
|
-
screencast.command("stop").description("Stop the screencast and emit frames (or write to disk).").option("-o, --out <dir>", "write frames as JPEGs into this directory (created if missing)").option("--gif", "after writing frames, ffmpeg them into <dir>.gif").option("--mp4", "after writing frames, ffmpeg them into <dir>.mp4").option("--fps <n>", "assumed framerate when invoking ffmpeg (default 15)", (v) => Number(v)).option("--no-dedupe", "keep raw frames; default collapses consecutive identical frames via SHA-256")
|
|
835
|
+
screencast.command("stop").description("Stop the screencast and emit frames (or write to disk).").option("-o, --out <dir>", "write frames as JPEGs into this directory (created if missing)").option("--gif", "after writing frames, ffmpeg them into <dir>.gif (requires ffmpeg on PATH)").option("--mp4", "after writing frames, ffmpeg them into <dir>.mp4 (requires ffmpeg on PATH)").option("--fps <n>", "assumed framerate when invoking ffmpeg (default 15)", (v) => Number(v)).option("--no-dedupe", "keep raw frames; default collapses consecutive identical frames via SHA-256").option("--allow-missing-ffmpeg", "with --gif/--mp4: skip ffmpeg step (and emit a warning) if ffmpeg isn't on PATH, instead of failing with external_dependency_missing")
|
|
732
836
|
).action(async (opts) => {
|
|
733
837
|
const args = { action: "stop" };
|
|
734
838
|
Object.assign(args, baseArgs(opts));
|
|
@@ -790,8 +894,22 @@ Notes:
|
|
|
790
894
|
const { spawnSync } = await import("child_process");
|
|
791
895
|
const which = spawnSync("which", ["ffmpeg"]);
|
|
792
896
|
if (which.status !== 0) {
|
|
793
|
-
|
|
794
|
-
|
|
897
|
+
if (opts.allowMissingFfmpeg) {
|
|
898
|
+
process.stderr.write("[chrome-relay] ffmpeg not on PATH \u2014 skipping --gif/--mp4 (allow-missing-ffmpeg).\n");
|
|
899
|
+
return;
|
|
900
|
+
}
|
|
901
|
+
const { RelayError: RelayError2 } = await Promise.resolve().then(() => (init_dist(), dist_exports));
|
|
902
|
+
const err = new RelayError2({
|
|
903
|
+
code: "external_dependency_missing",
|
|
904
|
+
message: "chrome-relay screencast stop --gif/--mp4 requires ffmpeg on PATH. Install ffmpeg (brew install ffmpeg) or pass --allow-missing-ffmpeg to skip the stitch step with a warning.",
|
|
905
|
+
tool: "chrome_screencast",
|
|
906
|
+
phase: "ffmpeg_stitch",
|
|
907
|
+
details: { dependency: "ffmpeg", outputs: { gif: !!opts.gif, mp4: !!opts.mp4 } },
|
|
908
|
+
retryable: false
|
|
909
|
+
});
|
|
910
|
+
process.stderr.write(err.message + "\n");
|
|
911
|
+
process.stderr.write(JSON.stringify({ relayError: err.toBridgeError() }, null, 2) + "\n");
|
|
912
|
+
process.exit(1);
|
|
795
913
|
}
|
|
796
914
|
if (opts.gif) {
|
|
797
915
|
const gifOut = `${opts.out.replace(/\/$/, "")}.gif`;
|
package/dist/index.js
CHANGED
package/dist/native-host.js
CHANGED
|
@@ -48,7 +48,7 @@ function toBridgeError(unknownErr, fallbackTool) {
|
|
|
48
48
|
}
|
|
49
49
|
|
|
50
50
|
// src/index.ts
|
|
51
|
-
var CHROME_RELAY_VERSION = true ? "0.5.
|
|
51
|
+
var CHROME_RELAY_VERSION = true ? "0.5.11" : "0.0.0-dev";
|
|
52
52
|
|
|
53
53
|
// src/release-notes.ts
|
|
54
54
|
function compareSemver(a, b) {
|