@thinkrun/cli 0.1.27
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/README.md +349 -0
- package/dist/bin/thinkrun.d.ts +6 -0
- package/dist/bin/thinkrun.d.ts.map +1 -0
- package/dist/bin/thinkrun.js +124 -0
- package/dist/bin/thinkrun.js.map +1 -0
- package/dist/scripts/browse.sh +1107 -0
- package/dist/src/adapters/cloud.d.ts +79 -0
- package/dist/src/adapters/cloud.d.ts.map +1 -0
- package/dist/src/adapters/cloud.js +637 -0
- package/dist/src/adapters/cloud.js.map +1 -0
- package/dist/src/adapters/index.d.ts +47 -0
- package/dist/src/adapters/index.d.ts.map +1 -0
- package/dist/src/adapters/index.js +211 -0
- package/dist/src/adapters/index.js.map +1 -0
- package/dist/src/adapters/local-command-retry.d.ts +12 -0
- package/dist/src/adapters/local-command-retry.d.ts.map +1 -0
- package/dist/src/adapters/local-command-retry.js +224 -0
- package/dist/src/adapters/local-command-retry.js.map +1 -0
- package/dist/src/adapters/local.d.ts +136 -0
- package/dist/src/adapters/local.d.ts.map +1 -0
- package/dist/src/adapters/local.js +1273 -0
- package/dist/src/adapters/local.js.map +1 -0
- package/dist/src/adapters/types.d.ts +45 -0
- package/dist/src/adapters/types.d.ts.map +1 -0
- package/dist/src/adapters/types.js +6 -0
- package/dist/src/adapters/types.js.map +1 -0
- package/dist/src/commands/actions.d.ts +135 -0
- package/dist/src/commands/actions.d.ts.map +1 -0
- package/dist/src/commands/actions.js +2207 -0
- package/dist/src/commands/actions.js.map +1 -0
- package/dist/src/commands/agent-init.d.ts +16 -0
- package/dist/src/commands/agent-init.d.ts.map +1 -0
- package/dist/src/commands/agent-init.js +222 -0
- package/dist/src/commands/agent-init.js.map +1 -0
- package/dist/src/commands/analyze.d.ts +11 -0
- package/dist/src/commands/analyze.d.ts.map +1 -0
- package/dist/src/commands/analyze.js +238 -0
- package/dist/src/commands/analyze.js.map +1 -0
- package/dist/src/commands/cache.d.ts +6 -0
- package/dist/src/commands/cache.d.ts.map +1 -0
- package/dist/src/commands/cache.js +147 -0
- package/dist/src/commands/cache.js.map +1 -0
- package/dist/src/commands/cloud.d.ts +6 -0
- package/dist/src/commands/cloud.d.ts.map +1 -0
- package/dist/src/commands/cloud.js +332 -0
- package/dist/src/commands/cloud.js.map +1 -0
- package/dist/src/commands/config.d.ts +7 -0
- package/dist/src/commands/config.d.ts.map +1 -0
- package/dist/src/commands/config.js +208 -0
- package/dist/src/commands/config.js.map +1 -0
- package/dist/src/commands/doctor.d.ts +127 -0
- package/dist/src/commands/doctor.d.ts.map +1 -0
- package/dist/src/commands/doctor.js +684 -0
- package/dist/src/commands/doctor.js.map +1 -0
- package/dist/src/commands/evaluate-helpers.d.ts +6 -0
- package/dist/src/commands/evaluate-helpers.d.ts.map +1 -0
- package/dist/src/commands/evaluate-helpers.js +13 -0
- package/dist/src/commands/evaluate-helpers.js.map +1 -0
- package/dist/src/commands/install.d.ts +118 -0
- package/dist/src/commands/install.d.ts.map +1 -0
- package/dist/src/commands/install.js +975 -0
- package/dist/src/commands/install.js.map +1 -0
- package/dist/src/commands/release.d.ts +7 -0
- package/dist/src/commands/release.d.ts.map +1 -0
- package/dist/src/commands/release.js +123 -0
- package/dist/src/commands/release.js.map +1 -0
- package/dist/src/commands/reset-connection.d.ts +17 -0
- package/dist/src/commands/reset-connection.d.ts.map +1 -0
- package/dist/src/commands/reset-connection.js +141 -0
- package/dist/src/commands/reset-connection.js.map +1 -0
- package/dist/src/commands/session-debug.d.ts +23 -0
- package/dist/src/commands/session-debug.d.ts.map +1 -0
- package/dist/src/commands/session-debug.js +267 -0
- package/dist/src/commands/session-debug.js.map +1 -0
- package/dist/src/commands/setup.d.ts +53 -0
- package/dist/src/commands/setup.d.ts.map +1 -0
- package/dist/src/commands/setup.js +249 -0
- package/dist/src/commands/setup.js.map +1 -0
- package/dist/src/config/store.d.ts +39 -0
- package/dist/src/config/store.d.ts.map +1 -0
- package/dist/src/config/store.js +290 -0
- package/dist/src/config/store.js.map +1 -0
- package/dist/src/daemon/access.d.ts +53 -0
- package/dist/src/daemon/access.d.ts.map +1 -0
- package/dist/src/daemon/access.js +87 -0
- package/dist/src/daemon/access.js.map +1 -0
- package/dist/src/daemon/bridge-envelope.d.ts +96 -0
- package/dist/src/daemon/bridge-envelope.d.ts.map +1 -0
- package/dist/src/daemon/bridge-envelope.js +235 -0
- package/dist/src/daemon/bridge-envelope.js.map +1 -0
- package/dist/src/daemon/utils.d.ts +43 -0
- package/dist/src/daemon/utils.d.ts.map +1 -0
- package/dist/src/daemon/utils.js +134 -0
- package/dist/src/daemon/utils.js.map +1 -0
- package/dist/src/errors.d.ts +60 -0
- package/dist/src/errors.d.ts.map +1 -0
- package/dist/src/errors.js +87 -0
- package/dist/src/errors.js.map +1 -0
- package/dist/src/local-bridge-timing.d.ts +31 -0
- package/dist/src/local-bridge-timing.d.ts.map +1 -0
- package/dist/src/local-bridge-timing.js +41 -0
- package/dist/src/local-bridge-timing.js.map +1 -0
- package/dist/src/obstacle-recovery/classify-script.d.ts +16 -0
- package/dist/src/obstacle-recovery/classify-script.d.ts.map +1 -0
- package/dist/src/obstacle-recovery/classify-script.js +53 -0
- package/dist/src/obstacle-recovery/classify-script.js.map +1 -0
- package/dist/src/obstacle-recovery/obstacle-classifier.d.ts +21 -0
- package/dist/src/obstacle-recovery/obstacle-classifier.d.ts.map +1 -0
- package/dist/src/obstacle-recovery/obstacle-classifier.js +37 -0
- package/dist/src/obstacle-recovery/obstacle-classifier.js.map +1 -0
- package/dist/src/obstacle-recovery/state-fingerprint.d.ts +26 -0
- package/dist/src/obstacle-recovery/state-fingerprint.d.ts.map +1 -0
- package/dist/src/obstacle-recovery/state-fingerprint.js +85 -0
- package/dist/src/obstacle-recovery/state-fingerprint.js.map +1 -0
- package/dist/src/obstacle-recovery/types.d.ts +44 -0
- package/dist/src/obstacle-recovery/types.d.ts.map +1 -0
- package/dist/src/obstacle-recovery/types.js +16 -0
- package/dist/src/obstacle-recovery/types.js.map +1 -0
- package/dist/src/output/formatter.d.ts +55 -0
- package/dist/src/output/formatter.d.ts.map +1 -0
- package/dist/src/output/formatter.js +55 -0
- package/dist/src/output/formatter.js.map +1 -0
- package/dist/src/output/mode.d.ts +11 -0
- package/dist/src/output/mode.d.ts.map +1 -0
- package/dist/src/output/mode.js +16 -0
- package/dist/src/output/mode.js.map +1 -0
- package/dist/src/protected-flow/detector.d.ts +26 -0
- package/dist/src/protected-flow/detector.d.ts.map +1 -0
- package/dist/src/protected-flow/detector.js +75 -0
- package/dist/src/protected-flow/detector.js.map +1 -0
- package/dist/src/protected-flow/types.d.ts +24 -0
- package/dist/src/protected-flow/types.d.ts.map +1 -0
- package/dist/src/protected-flow/types.js +28 -0
- package/dist/src/protected-flow/types.js.map +1 -0
- package/dist/src/session/agent-identity.d.ts +65 -0
- package/dist/src/session/agent-identity.d.ts.map +1 -0
- package/dist/src/session/agent-identity.js +133 -0
- package/dist/src/session/agent-identity.js.map +1 -0
- package/dist/src/session/cli-session-sync.d.ts +72 -0
- package/dist/src/session/cli-session-sync.d.ts.map +1 -0
- package/dist/src/session/cli-session-sync.js +244 -0
- package/dist/src/session/cli-session-sync.js.map +1 -0
- package/dist/src/session/context.d.ts +24 -0
- package/dist/src/session/context.d.ts.map +1 -0
- package/dist/src/session/context.js +165 -0
- package/dist/src/session/context.js.map +1 -0
- package/dist/src/session/continuity.d.ts +33 -0
- package/dist/src/session/continuity.d.ts.map +1 -0
- package/dist/src/session/continuity.js +179 -0
- package/dist/src/session/continuity.js.map +1 -0
- package/dist/src/session/errors.d.ts +9 -0
- package/dist/src/session/errors.d.ts.map +1 -0
- package/dist/src/session/errors.js +31 -0
- package/dist/src/session/errors.js.map +1 -0
- package/dist/src/session/local-continuity.d.ts +16 -0
- package/dist/src/session/local-continuity.d.ts.map +1 -0
- package/dist/src/session/local-continuity.js +146 -0
- package/dist/src/session/local-continuity.js.map +1 -0
- package/dist/src/session/signal-handler.d.ts +24 -0
- package/dist/src/session/signal-handler.d.ts.map +1 -0
- package/dist/src/session/signal-handler.js +35 -0
- package/dist/src/session/signal-handler.js.map +1 -0
- package/dist/src/shared/local-recovery-policy.d.ts +40 -0
- package/dist/src/shared/local-recovery-policy.d.ts.map +1 -0
- package/dist/src/shared/local-recovery-policy.js +59 -0
- package/dist/src/shared/local-recovery-policy.js.map +1 -0
- package/dist/src/shared/recovery-state.d.ts +3 -0
- package/dist/src/shared/recovery-state.d.ts.map +1 -0
- package/dist/src/shared/recovery-state.js +9 -0
- package/dist/src/shared/recovery-state.js.map +1 -0
- package/dist/src/types.d.ts +131 -0
- package/dist/src/types.d.ts.map +1 -0
- package/dist/src/types.js +5 -0
- package/dist/src/types.js.map +1 -0
- package/dist/src/utils.d.ts +50 -0
- package/dist/src/utils.d.ts.map +1 -0
- package/dist/src/utils.js +147 -0
- package/dist/src/utils.js.map +1 -0
- package/dist/src/working-location.d.ts +107 -0
- package/dist/src/working-location.d.ts.map +1 -0
- package/dist/src/working-location.js +651 -0
- package/dist/src/working-location.js.map +1 -0
- package/package.json +65 -0
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Adapter factory — resolves local vs cloud from stored session context first,
|
|
3
|
+
* then falls back to environment reachability when no context exists.
|
|
4
|
+
*/
|
|
5
|
+
import type { BrowserAdapter } from './types.js';
|
|
6
|
+
export type AdapterTarget = 'local' | 'cloud';
|
|
7
|
+
export type PreferredMode = 'local' | 'cloud';
|
|
8
|
+
export declare function resolveAdapterTarget(opts: {
|
|
9
|
+
hasApiKey: boolean;
|
|
10
|
+
hasNativeHost: boolean;
|
|
11
|
+
contextMode?: 'local' | 'cloud';
|
|
12
|
+
preferredMode?: PreferredMode;
|
|
13
|
+
}): AdapterTarget;
|
|
14
|
+
export type ResolutionInfo = {
|
|
15
|
+
resolvedMode: AdapterTarget | null;
|
|
16
|
+
modeSource: 'explicit_local' | 'explicit_cloud' | 'context_local' | 'context_cloud' | 'fallback_local' | 'needs_explicit_cloud' | 'unavailable';
|
|
17
|
+
contextMode: 'local' | 'cloud' | undefined;
|
|
18
|
+
hasApiKey: boolean;
|
|
19
|
+
hasNativeHost: boolean;
|
|
20
|
+
bridgePort: number | undefined;
|
|
21
|
+
error?: string;
|
|
22
|
+
};
|
|
23
|
+
export declare function resolveReachableBridgePort(opts?: {
|
|
24
|
+
preferredMode?: PreferredMode;
|
|
25
|
+
contextMode?: 'local' | 'cloud';
|
|
26
|
+
readPort?: () => number | undefined;
|
|
27
|
+
probePort?: (port: number) => Promise<boolean>;
|
|
28
|
+
maxAttempts?: number;
|
|
29
|
+
}): Promise<{
|
|
30
|
+
port: number | undefined;
|
|
31
|
+
reachable: boolean;
|
|
32
|
+
}>;
|
|
33
|
+
/**
|
|
34
|
+
* Returns resolution metadata for the next command (no preferredMode) or for an explicit mode.
|
|
35
|
+
* Does not throw; use for session debug and doctor.
|
|
36
|
+
*/
|
|
37
|
+
export declare function getResolutionInfo(preferredMode?: PreferredMode): Promise<ResolutionInfo>;
|
|
38
|
+
export declare function getAdapter(preferredMode?: PreferredMode, tabOverride?: string): Promise<BrowserAdapter>;
|
|
39
|
+
/**
|
|
40
|
+
* Returns true if the native host is running and healthy at the given port.
|
|
41
|
+
* Fast timeout (2s) so commands don't hang on startup.
|
|
42
|
+
*/
|
|
43
|
+
export declare function checkNativeHost(port?: number): Promise<boolean>;
|
|
44
|
+
export { CloudAdapter } from './cloud.js';
|
|
45
|
+
export { LocalAdapter } from './local.js';
|
|
46
|
+
export type { BrowserAdapter } from './types.js';
|
|
47
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/adapters/index.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAIH,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,YAAY,CAAC;AAWjD,MAAM,MAAM,aAAa,GAAG,OAAO,GAAG,OAAO,CAAC;AAC9C,MAAM,MAAM,aAAa,GAAG,OAAO,GAAG,OAAO,CAAC;AAE9C,wBAAgB,oBAAoB,CAAC,IAAI,EAAE;IACzC,SAAS,EAAE,OAAO,CAAC;IACnB,aAAa,EAAE,OAAO,CAAC;IACvB,WAAW,CAAC,EAAE,OAAO,GAAG,OAAO,CAAC;IAChC,aAAa,CAAC,EAAE,aAAa,CAAC;CAC/B,GAAG,aAAa,CAoChB;AAED,MAAM,MAAM,cAAc,GAAG;IAC3B,YAAY,EAAE,aAAa,GAAG,IAAI,CAAC;IACnC,UAAU,EAAE,gBAAgB,GAAG,gBAAgB,GAAG,eAAe,GAAG,eAAe,GAAG,gBAAgB,GAAG,sBAAsB,GAAG,aAAa,CAAC;IAChJ,WAAW,EAAE,OAAO,GAAG,OAAO,GAAG,SAAS,CAAC;IAC3C,SAAS,EAAE,OAAO,CAAC;IACnB,aAAa,EAAE,OAAO,CAAC;IACvB,UAAU,EAAE,MAAM,GAAG,SAAS,CAAC;IAC/B,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB,CAAC;AAUF,wBAAsB,0BAA0B,CAAC,IAAI,GAAE;IACrD,aAAa,CAAC,EAAE,aAAa,CAAC;IAC9B,WAAW,CAAC,EAAE,OAAO,GAAG,OAAO,CAAC;IAChC,QAAQ,CAAC,EAAE,MAAM,MAAM,GAAG,SAAS,CAAC;IACpC,SAAS,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,OAAO,CAAC,OAAO,CAAC,CAAC;IAC/C,WAAW,CAAC,EAAE,MAAM,CAAC;CACjB,GAAG,OAAO,CAAC;IAAE,IAAI,EAAE,MAAM,GAAG,SAAS,CAAC;IAAC,SAAS,EAAE,OAAO,CAAA;CAAE,CAAC,CAsCjE;AAED;;;GAGG;AACH,wBAAsB,iBAAiB,CAAC,aAAa,CAAC,EAAE,aAAa,GAAG,OAAO,CAAC,cAAc,CAAC,CA2E9F;AAED,wBAAsB,UAAU,CAAC,aAAa,CAAC,EAAE,aAAa,EAAE,WAAW,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,cAAc,CAAC,CA+B7G;AAED;;;GAGG;AACH,wBAAsB,eAAe,CAAC,IAAI,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAYrE;AAED,OAAO,EAAE,YAAY,EAAE,MAAM,YAAY,CAAC;AAC1C,OAAO,EAAE,YAAY,EAAE,MAAM,YAAY,CAAC;AAC1C,YAAY,EAAE,cAAc,EAAE,MAAM,YAAY,CAAC"}
|
|
@@ -0,0 +1,211 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Adapter factory — resolves local vs cloud from stored session context first,
|
|
3
|
+
* then falls back to environment reachability when no context exists.
|
|
4
|
+
*/
|
|
5
|
+
import { CloudAdapter } from './cloud.js';
|
|
6
|
+
import { LocalAdapter } from './local.js';
|
|
7
|
+
import { ApiError } from '../errors.js';
|
|
8
|
+
import { config } from '../config/store.js';
|
|
9
|
+
import { readBridgePort } from '../utils.js';
|
|
10
|
+
import { getSessionContext } from '../session/context.js';
|
|
11
|
+
import { cloudSessionMissingApiKeyError, localSessionBridgeUnavailableError, noConnectionError, } from '../session/errors.js';
|
|
12
|
+
export function resolveAdapterTarget(opts) {
|
|
13
|
+
const { hasApiKey, hasNativeHost, contextMode, preferredMode } = opts;
|
|
14
|
+
if (preferredMode === 'local') {
|
|
15
|
+
if (!hasNativeHost) {
|
|
16
|
+
throw localSessionBridgeUnavailableError();
|
|
17
|
+
}
|
|
18
|
+
return 'local';
|
|
19
|
+
}
|
|
20
|
+
if (preferredMode === 'cloud') {
|
|
21
|
+
if (!hasApiKey) {
|
|
22
|
+
throw cloudSessionMissingApiKeyError();
|
|
23
|
+
}
|
|
24
|
+
return 'cloud';
|
|
25
|
+
}
|
|
26
|
+
if (contextMode === 'local') {
|
|
27
|
+
if (!hasNativeHost) {
|
|
28
|
+
throw localSessionBridgeUnavailableError();
|
|
29
|
+
}
|
|
30
|
+
return 'local';
|
|
31
|
+
}
|
|
32
|
+
if (contextMode === 'cloud') {
|
|
33
|
+
if (!hasApiKey) {
|
|
34
|
+
throw cloudSessionMissingApiKeyError();
|
|
35
|
+
}
|
|
36
|
+
return 'cloud';
|
|
37
|
+
}
|
|
38
|
+
if (hasNativeHost)
|
|
39
|
+
return 'local';
|
|
40
|
+
// Local is the default — do not silently fall back to cloud.
|
|
41
|
+
// Cloud must be explicit: --mode cloud, or a prior `thinkrun cloud start`.
|
|
42
|
+
throw noConnectionError();
|
|
43
|
+
}
|
|
44
|
+
/** One re-read after delay; worst-case ~250ms extra when the host is down. */
|
|
45
|
+
const BRIDGE_PORT_RETRY_ATTEMPTS = 2;
|
|
46
|
+
const BRIDGE_PORT_RETRY_DELAY_MS = 250;
|
|
47
|
+
function delay(ms) {
|
|
48
|
+
return new Promise((resolve) => setTimeout(resolve, ms));
|
|
49
|
+
}
|
|
50
|
+
export async function resolveReachableBridgePort(opts = {}) {
|
|
51
|
+
const { preferredMode, contextMode, readPort = readBridgePort, probePort = checkNativeHost, maxAttempts = BRIDGE_PORT_RETRY_ATTEMPTS, } = opts;
|
|
52
|
+
const shouldProbeNativeHost = preferredMode === 'local' ||
|
|
53
|
+
(preferredMode !== 'cloud' && contextMode !== 'cloud');
|
|
54
|
+
if (!shouldProbeNativeHost) {
|
|
55
|
+
return { port: undefined, reachable: false };
|
|
56
|
+
}
|
|
57
|
+
let lastPort;
|
|
58
|
+
const raw = maxAttempts ?? BRIDGE_PORT_RETRY_ATTEMPTS;
|
|
59
|
+
const parsed = Number(raw);
|
|
60
|
+
const attempts = Math.max(1, Math.min(50, Number.isFinite(parsed) ? Math.floor(parsed) : BRIDGE_PORT_RETRY_ATTEMPTS));
|
|
61
|
+
for (let attempt = 0; attempt < attempts; attempt += 1) {
|
|
62
|
+
const port = readPort();
|
|
63
|
+
lastPort = port;
|
|
64
|
+
try {
|
|
65
|
+
if (port !== undefined && (await probePort(port))) {
|
|
66
|
+
return { port, reachable: true };
|
|
67
|
+
}
|
|
68
|
+
}
|
|
69
|
+
catch {
|
|
70
|
+
/* Treat probe rejection as unreachable; continue to re-read port / retry. */
|
|
71
|
+
}
|
|
72
|
+
if (attempt < attempts - 1) {
|
|
73
|
+
await delay(BRIDGE_PORT_RETRY_DELAY_MS);
|
|
74
|
+
}
|
|
75
|
+
}
|
|
76
|
+
return { port: lastPort, reachable: false };
|
|
77
|
+
}
|
|
78
|
+
/**
|
|
79
|
+
* Returns resolution metadata for the next command (no preferredMode) or for an explicit mode.
|
|
80
|
+
* Does not throw; use for session debug and doctor.
|
|
81
|
+
*/
|
|
82
|
+
export async function getResolutionInfo(preferredMode) {
|
|
83
|
+
const apiKey = config.get('apiKey');
|
|
84
|
+
let context;
|
|
85
|
+
try {
|
|
86
|
+
context = getSessionContext();
|
|
87
|
+
}
|
|
88
|
+
catch {
|
|
89
|
+
return {
|
|
90
|
+
resolvedMode: null,
|
|
91
|
+
modeSource: 'unavailable',
|
|
92
|
+
contextMode: undefined,
|
|
93
|
+
hasApiKey: !!apiKey,
|
|
94
|
+
hasNativeHost: false,
|
|
95
|
+
bridgePort: undefined,
|
|
96
|
+
error: 'Mixed or invalid session context',
|
|
97
|
+
};
|
|
98
|
+
}
|
|
99
|
+
const bridge = await resolveReachableBridgePort({
|
|
100
|
+
preferredMode,
|
|
101
|
+
contextMode: context?.mode,
|
|
102
|
+
});
|
|
103
|
+
const port = bridge.port;
|
|
104
|
+
const isReachable = bridge.reachable;
|
|
105
|
+
try {
|
|
106
|
+
const target = resolveAdapterTarget({
|
|
107
|
+
hasApiKey: !!apiKey,
|
|
108
|
+
hasNativeHost: isReachable,
|
|
109
|
+
contextMode: context?.mode,
|
|
110
|
+
preferredMode,
|
|
111
|
+
});
|
|
112
|
+
const modeSource = preferredMode === 'local'
|
|
113
|
+
? 'explicit_local'
|
|
114
|
+
: preferredMode === 'cloud'
|
|
115
|
+
? 'explicit_cloud'
|
|
116
|
+
: context?.mode === 'local'
|
|
117
|
+
? 'context_local'
|
|
118
|
+
: context?.mode === 'cloud'
|
|
119
|
+
? 'context_cloud'
|
|
120
|
+
: 'fallback_local';
|
|
121
|
+
return {
|
|
122
|
+
resolvedMode: target,
|
|
123
|
+
modeSource,
|
|
124
|
+
contextMode: context?.mode,
|
|
125
|
+
hasApiKey: !!apiKey,
|
|
126
|
+
hasNativeHost: isReachable,
|
|
127
|
+
bridgePort: port,
|
|
128
|
+
};
|
|
129
|
+
}
|
|
130
|
+
catch (e) {
|
|
131
|
+
// Mirror the success-path modeSource logic so that explicit/context modes
|
|
132
|
+
// are preserved in diagnostics even when resolution fails.
|
|
133
|
+
// 'needs_explicit_cloud' is reserved for the no-context, no-host, has-key
|
|
134
|
+
// case — not for local/cloud context failures.
|
|
135
|
+
const modeSource = preferredMode === 'local'
|
|
136
|
+
? 'explicit_local'
|
|
137
|
+
: preferredMode === 'cloud'
|
|
138
|
+
? 'explicit_cloud'
|
|
139
|
+
: context?.mode === 'local'
|
|
140
|
+
? 'context_local'
|
|
141
|
+
: context?.mode === 'cloud'
|
|
142
|
+
? 'context_cloud'
|
|
143
|
+
: !isReachable && !!apiKey
|
|
144
|
+
? 'needs_explicit_cloud'
|
|
145
|
+
: 'unavailable';
|
|
146
|
+
return {
|
|
147
|
+
resolvedMode: null,
|
|
148
|
+
modeSource,
|
|
149
|
+
contextMode: context?.mode,
|
|
150
|
+
hasApiKey: !!apiKey,
|
|
151
|
+
hasNativeHost: isReachable,
|
|
152
|
+
bridgePort: port,
|
|
153
|
+
error: e instanceof Error ? e.message : String(e),
|
|
154
|
+
};
|
|
155
|
+
}
|
|
156
|
+
}
|
|
157
|
+
export async function getAdapter(preferredMode, tabOverride) {
|
|
158
|
+
const apiKey = config.get('apiKey');
|
|
159
|
+
let context;
|
|
160
|
+
try {
|
|
161
|
+
context = getSessionContext();
|
|
162
|
+
}
|
|
163
|
+
catch (error) {
|
|
164
|
+
if (error instanceof ApiError)
|
|
165
|
+
throw error;
|
|
166
|
+
throw new ApiError(error.message || 'Invalid session context');
|
|
167
|
+
}
|
|
168
|
+
const bridge = await resolveReachableBridgePort({
|
|
169
|
+
preferredMode,
|
|
170
|
+
contextMode: context?.mode,
|
|
171
|
+
});
|
|
172
|
+
const port = bridge.port;
|
|
173
|
+
const isReachable = bridge.reachable;
|
|
174
|
+
const target = resolveAdapterTarget({
|
|
175
|
+
hasApiKey: !!apiKey,
|
|
176
|
+
hasNativeHost: isReachable,
|
|
177
|
+
contextMode: context?.mode,
|
|
178
|
+
preferredMode,
|
|
179
|
+
});
|
|
180
|
+
if (target === 'cloud') {
|
|
181
|
+
if (!apiKey)
|
|
182
|
+
throw cloudSessionMissingApiKeyError();
|
|
183
|
+
if (tabOverride) {
|
|
184
|
+
process.stderr.write('[thinkrun] Warning: --tab is not supported in cloud mode, ignoring\n');
|
|
185
|
+
}
|
|
186
|
+
return new CloudAdapter(apiKey);
|
|
187
|
+
}
|
|
188
|
+
return new LocalAdapter(port, undefined, tabOverride);
|
|
189
|
+
}
|
|
190
|
+
/**
|
|
191
|
+
* Returns true if the native host is running and healthy at the given port.
|
|
192
|
+
* Fast timeout (2s) so commands don't hang on startup.
|
|
193
|
+
*/
|
|
194
|
+
export async function checkNativeHost(port) {
|
|
195
|
+
const resolvedPort = port ?? readBridgePort();
|
|
196
|
+
try {
|
|
197
|
+
const response = await fetch(`http://127.0.0.1:${resolvedPort}/health`, {
|
|
198
|
+
signal: AbortSignal.timeout(2000),
|
|
199
|
+
});
|
|
200
|
+
if (!response.ok)
|
|
201
|
+
return false;
|
|
202
|
+
const json = (await response.json());
|
|
203
|
+
return json?.data?.status === 'ok';
|
|
204
|
+
}
|
|
205
|
+
catch {
|
|
206
|
+
return false;
|
|
207
|
+
}
|
|
208
|
+
}
|
|
209
|
+
export { CloudAdapter } from './cloud.js';
|
|
210
|
+
export { LocalAdapter } from './local.js';
|
|
211
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/adapters/index.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
export type LocalCommandRetryKey = 'get_session' | 'list_tabs' | 'navigate' | 'go_back' | 'go_forward' | 'click' | 'fill' | 'type' | 'press' | 'hover' | 'select' | 'wait' | 'wait_for_text' | 'evaluate' | 'screenshot' | 'snapshot' | 'extract' | 'scroll' | 'get_url' | 'get_title' | 'get_html' | 'handle_dialog' | 'get_console_logs' | 'get_network_logs' | 'clear_logs' | 'unknown';
|
|
2
|
+
export type TransportReplayPolicy = 'safe_same_bridge' | 'only_after_route_change' | 'never';
|
|
3
|
+
export type TransportOutcomeRisk = 'no_side_effect_if_retried' | 'unknown_if_request_left_process';
|
|
4
|
+
export type LocalCommandRetryProfile = {
|
|
5
|
+
key: LocalCommandRetryKey;
|
|
6
|
+
description: string;
|
|
7
|
+
transportReplay: TransportReplayPolicy;
|
|
8
|
+
outcomeRisk: TransportOutcomeRisk;
|
|
9
|
+
};
|
|
10
|
+
export declare function getLocalCommandRetryProfileFromPath(path: string, method: string): LocalCommandRetryProfile;
|
|
11
|
+
export declare function isSafelyReplayableOnSameBridge(profile: LocalCommandRetryProfile): boolean;
|
|
12
|
+
//# sourceMappingURL=local-command-retry.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"local-command-retry.d.ts","sourceRoot":"","sources":["../../../src/adapters/local-command-retry.ts"],"names":[],"mappings":"AAAA,MAAM,MAAM,oBAAoB,GAC5B,aAAa,GACb,WAAW,GACX,UAAU,GACV,SAAS,GACT,YAAY,GACZ,OAAO,GACP,MAAM,GACN,MAAM,GACN,OAAO,GACP,OAAO,GACP,QAAQ,GACR,MAAM,GACN,eAAe,GACf,UAAU,GACV,YAAY,GACZ,UAAU,GACV,SAAS,GACT,QAAQ,GACR,SAAS,GACT,WAAW,GACX,UAAU,GACV,eAAe,GACf,kBAAkB,GAClB,kBAAkB,GAClB,YAAY,GACZ,SAAS,CAAC;AAEd,MAAM,MAAM,qBAAqB,GAC7B,kBAAkB,GAClB,yBAAyB,GACzB,OAAO,CAAC;AAEZ,MAAM,MAAM,oBAAoB,GAC5B,2BAA2B,GAC3B,iCAAiC,CAAC;AAEtC,MAAM,MAAM,wBAAwB,GAAG;IACrC,GAAG,EAAE,oBAAoB,CAAC;IAC1B,WAAW,EAAE,MAAM,CAAC;IACpB,eAAe,EAAE,qBAAqB,CAAC;IAGvC,WAAW,EAAE,oBAAoB,CAAC;CACnC,CAAC;AAiKF,wBAAgB,mCAAmC,CACjD,IAAI,EAAE,MAAM,EACZ,MAAM,EAAE,MAAM,GACb,wBAAwB,CA6D1B;AAED,wBAAgB,8BAA8B,CAAC,OAAO,EAAE,wBAAwB,GAAG,OAAO,CAKzF"}
|
|
@@ -0,0 +1,224 @@
|
|
|
1
|
+
const LOCAL_COMMAND_RETRY_PROFILES = {
|
|
2
|
+
get_session: {
|
|
3
|
+
key: 'get_session',
|
|
4
|
+
description: 'Read current tab state',
|
|
5
|
+
transportReplay: 'safe_same_bridge',
|
|
6
|
+
outcomeRisk: 'no_side_effect_if_retried',
|
|
7
|
+
},
|
|
8
|
+
list_tabs: {
|
|
9
|
+
key: 'list_tabs',
|
|
10
|
+
description: 'List visible tabs and ownership metadata',
|
|
11
|
+
transportReplay: 'safe_same_bridge',
|
|
12
|
+
outcomeRisk: 'no_side_effect_if_retried',
|
|
13
|
+
},
|
|
14
|
+
navigate: {
|
|
15
|
+
key: 'navigate',
|
|
16
|
+
description: 'Change the page URL',
|
|
17
|
+
transportReplay: 'only_after_route_change',
|
|
18
|
+
outcomeRisk: 'unknown_if_request_left_process',
|
|
19
|
+
},
|
|
20
|
+
go_back: {
|
|
21
|
+
key: 'go_back',
|
|
22
|
+
description: 'Navigate browser history backward',
|
|
23
|
+
transportReplay: 'only_after_route_change',
|
|
24
|
+
outcomeRisk: 'unknown_if_request_left_process',
|
|
25
|
+
},
|
|
26
|
+
go_forward: {
|
|
27
|
+
key: 'go_forward',
|
|
28
|
+
description: 'Navigate browser history forward',
|
|
29
|
+
transportReplay: 'only_after_route_change',
|
|
30
|
+
outcomeRisk: 'unknown_if_request_left_process',
|
|
31
|
+
},
|
|
32
|
+
click: {
|
|
33
|
+
key: 'click',
|
|
34
|
+
description: 'Mutate page state via click',
|
|
35
|
+
transportReplay: 'only_after_route_change',
|
|
36
|
+
outcomeRisk: 'unknown_if_request_left_process',
|
|
37
|
+
},
|
|
38
|
+
fill: {
|
|
39
|
+
key: 'fill',
|
|
40
|
+
description: 'Mutate page state via form fill',
|
|
41
|
+
transportReplay: 'only_after_route_change',
|
|
42
|
+
outcomeRisk: 'unknown_if_request_left_process',
|
|
43
|
+
},
|
|
44
|
+
type: {
|
|
45
|
+
key: 'type',
|
|
46
|
+
description: 'Mutate page state via text entry',
|
|
47
|
+
transportReplay: 'only_after_route_change',
|
|
48
|
+
outcomeRisk: 'unknown_if_request_left_process',
|
|
49
|
+
},
|
|
50
|
+
press: {
|
|
51
|
+
key: 'press',
|
|
52
|
+
description: 'Mutate page state via keyboard input',
|
|
53
|
+
transportReplay: 'only_after_route_change',
|
|
54
|
+
outcomeRisk: 'unknown_if_request_left_process',
|
|
55
|
+
},
|
|
56
|
+
hover: {
|
|
57
|
+
key: 'hover',
|
|
58
|
+
description: 'Pointer movement that may trigger page behavior',
|
|
59
|
+
transportReplay: 'only_after_route_change',
|
|
60
|
+
outcomeRisk: 'unknown_if_request_left_process',
|
|
61
|
+
},
|
|
62
|
+
select: {
|
|
63
|
+
key: 'select',
|
|
64
|
+
description: 'Mutate form selection state',
|
|
65
|
+
transportReplay: 'only_after_route_change',
|
|
66
|
+
outcomeRisk: 'unknown_if_request_left_process',
|
|
67
|
+
},
|
|
68
|
+
wait: {
|
|
69
|
+
key: 'wait',
|
|
70
|
+
description: 'Observe page state until a condition is met',
|
|
71
|
+
transportReplay: 'safe_same_bridge',
|
|
72
|
+
outcomeRisk: 'no_side_effect_if_retried',
|
|
73
|
+
},
|
|
74
|
+
wait_for_text: {
|
|
75
|
+
key: 'wait_for_text',
|
|
76
|
+
description: 'Observe page text until a condition is met',
|
|
77
|
+
transportReplay: 'safe_same_bridge',
|
|
78
|
+
outcomeRisk: 'no_side_effect_if_retried',
|
|
79
|
+
},
|
|
80
|
+
evaluate: {
|
|
81
|
+
key: 'evaluate',
|
|
82
|
+
description: 'Arbitrary JavaScript execution',
|
|
83
|
+
transportReplay: 'never',
|
|
84
|
+
outcomeRisk: 'unknown_if_request_left_process',
|
|
85
|
+
},
|
|
86
|
+
screenshot: {
|
|
87
|
+
key: 'screenshot',
|
|
88
|
+
description: 'Capture current visual state',
|
|
89
|
+
transportReplay: 'never',
|
|
90
|
+
outcomeRisk: 'unknown_if_request_left_process',
|
|
91
|
+
},
|
|
92
|
+
snapshot: {
|
|
93
|
+
key: 'snapshot',
|
|
94
|
+
description: 'Capture current DOM/accessibility state',
|
|
95
|
+
transportReplay: 'safe_same_bridge',
|
|
96
|
+
outcomeRisk: 'no_side_effect_if_retried',
|
|
97
|
+
},
|
|
98
|
+
extract: {
|
|
99
|
+
key: 'extract',
|
|
100
|
+
description: 'Read page content or element data',
|
|
101
|
+
transportReplay: 'safe_same_bridge',
|
|
102
|
+
outcomeRisk: 'no_side_effect_if_retried',
|
|
103
|
+
},
|
|
104
|
+
scroll: {
|
|
105
|
+
key: 'scroll',
|
|
106
|
+
description: 'Mutate viewport position',
|
|
107
|
+
transportReplay: 'only_after_route_change',
|
|
108
|
+
outcomeRisk: 'unknown_if_request_left_process',
|
|
109
|
+
},
|
|
110
|
+
get_url: {
|
|
111
|
+
key: 'get_url',
|
|
112
|
+
description: 'Read current page URL',
|
|
113
|
+
transportReplay: 'safe_same_bridge',
|
|
114
|
+
outcomeRisk: 'no_side_effect_if_retried',
|
|
115
|
+
},
|
|
116
|
+
get_title: {
|
|
117
|
+
key: 'get_title',
|
|
118
|
+
description: 'Read current page title',
|
|
119
|
+
transportReplay: 'safe_same_bridge',
|
|
120
|
+
outcomeRisk: 'no_side_effect_if_retried',
|
|
121
|
+
},
|
|
122
|
+
get_html: {
|
|
123
|
+
key: 'get_html',
|
|
124
|
+
description: 'Read current document HTML',
|
|
125
|
+
transportReplay: 'safe_same_bridge',
|
|
126
|
+
outcomeRisk: 'no_side_effect_if_retried',
|
|
127
|
+
},
|
|
128
|
+
handle_dialog: {
|
|
129
|
+
key: 'handle_dialog',
|
|
130
|
+
description: 'Accept or dismiss browser dialog',
|
|
131
|
+
transportReplay: 'only_after_route_change',
|
|
132
|
+
outcomeRisk: 'unknown_if_request_left_process',
|
|
133
|
+
},
|
|
134
|
+
get_console_logs: {
|
|
135
|
+
key: 'get_console_logs',
|
|
136
|
+
description: 'Read console log buffer',
|
|
137
|
+
transportReplay: 'safe_same_bridge',
|
|
138
|
+
outcomeRisk: 'no_side_effect_if_retried',
|
|
139
|
+
},
|
|
140
|
+
get_network_logs: {
|
|
141
|
+
key: 'get_network_logs',
|
|
142
|
+
description: 'Read network log buffer',
|
|
143
|
+
transportReplay: 'safe_same_bridge',
|
|
144
|
+
outcomeRisk: 'no_side_effect_if_retried',
|
|
145
|
+
},
|
|
146
|
+
clear_logs: {
|
|
147
|
+
key: 'clear_logs',
|
|
148
|
+
description: 'Clear buffered console/network logs',
|
|
149
|
+
transportReplay: 'only_after_route_change',
|
|
150
|
+
outcomeRisk: 'unknown_if_request_left_process',
|
|
151
|
+
},
|
|
152
|
+
unknown: {
|
|
153
|
+
key: 'unknown',
|
|
154
|
+
description: 'Unknown local bridge command',
|
|
155
|
+
transportReplay: 'never',
|
|
156
|
+
outcomeRisk: 'unknown_if_request_left_process',
|
|
157
|
+
},
|
|
158
|
+
};
|
|
159
|
+
export function getLocalCommandRetryProfileFromPath(path, method) {
|
|
160
|
+
const normalizedMethod = method.toUpperCase();
|
|
161
|
+
if (normalizedMethod === 'GET' && path === '/tabs') {
|
|
162
|
+
return LOCAL_COMMAND_RETRY_PROFILES.list_tabs;
|
|
163
|
+
}
|
|
164
|
+
if (normalizedMethod === 'GET' && /^\/sessions\/[^/]+$/.test(path)) {
|
|
165
|
+
return LOCAL_COMMAND_RETRY_PROFILES.get_session;
|
|
166
|
+
}
|
|
167
|
+
const actionMatch = path.match(/^\/sessions\/[^/]+\/([a-z-]+)$/);
|
|
168
|
+
const action = actionMatch?.[1];
|
|
169
|
+
switch (action) {
|
|
170
|
+
case 'navigate':
|
|
171
|
+
return LOCAL_COMMAND_RETRY_PROFILES.navigate;
|
|
172
|
+
case 'go-back':
|
|
173
|
+
return LOCAL_COMMAND_RETRY_PROFILES.go_back;
|
|
174
|
+
case 'go-forward':
|
|
175
|
+
return LOCAL_COMMAND_RETRY_PROFILES.go_forward;
|
|
176
|
+
case 'click':
|
|
177
|
+
return LOCAL_COMMAND_RETRY_PROFILES.click;
|
|
178
|
+
case 'fill':
|
|
179
|
+
return LOCAL_COMMAND_RETRY_PROFILES.fill;
|
|
180
|
+
case 'type':
|
|
181
|
+
return LOCAL_COMMAND_RETRY_PROFILES.type;
|
|
182
|
+
case 'press':
|
|
183
|
+
return LOCAL_COMMAND_RETRY_PROFILES.press;
|
|
184
|
+
case 'hover':
|
|
185
|
+
return LOCAL_COMMAND_RETRY_PROFILES.hover;
|
|
186
|
+
case 'select':
|
|
187
|
+
return LOCAL_COMMAND_RETRY_PROFILES.select;
|
|
188
|
+
case 'wait':
|
|
189
|
+
return LOCAL_COMMAND_RETRY_PROFILES.wait;
|
|
190
|
+
case 'wait-for-text':
|
|
191
|
+
return LOCAL_COMMAND_RETRY_PROFILES.wait_for_text;
|
|
192
|
+
case 'evaluate':
|
|
193
|
+
return LOCAL_COMMAND_RETRY_PROFILES.evaluate;
|
|
194
|
+
case 'screenshot':
|
|
195
|
+
return LOCAL_COMMAND_RETRY_PROFILES.screenshot;
|
|
196
|
+
case 'snapshot':
|
|
197
|
+
return LOCAL_COMMAND_RETRY_PROFILES.snapshot;
|
|
198
|
+
case 'extract':
|
|
199
|
+
return LOCAL_COMMAND_RETRY_PROFILES.extract;
|
|
200
|
+
case 'scroll':
|
|
201
|
+
return LOCAL_COMMAND_RETRY_PROFILES.scroll;
|
|
202
|
+
case 'url':
|
|
203
|
+
return LOCAL_COMMAND_RETRY_PROFILES.get_url;
|
|
204
|
+
case 'title':
|
|
205
|
+
return LOCAL_COMMAND_RETRY_PROFILES.get_title;
|
|
206
|
+
case 'html':
|
|
207
|
+
return LOCAL_COMMAND_RETRY_PROFILES.get_html;
|
|
208
|
+
case 'dialog':
|
|
209
|
+
return LOCAL_COMMAND_RETRY_PROFILES.handle_dialog;
|
|
210
|
+
case 'console':
|
|
211
|
+
return LOCAL_COMMAND_RETRY_PROFILES.get_console_logs;
|
|
212
|
+
case 'network':
|
|
213
|
+
return LOCAL_COMMAND_RETRY_PROFILES.get_network_logs;
|
|
214
|
+
case 'clear-logs':
|
|
215
|
+
return LOCAL_COMMAND_RETRY_PROFILES.clear_logs;
|
|
216
|
+
default:
|
|
217
|
+
return LOCAL_COMMAND_RETRY_PROFILES.unknown;
|
|
218
|
+
}
|
|
219
|
+
}
|
|
220
|
+
export function isSafelyReplayableOnSameBridge(profile) {
|
|
221
|
+
return (profile.transportReplay === 'safe_same_bridge'
|
|
222
|
+
&& profile.outcomeRisk === 'no_side_effect_if_retried');
|
|
223
|
+
}
|
|
224
|
+
//# sourceMappingURL=local-command-retry.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"local-command-retry.js","sourceRoot":"","sources":["../../../src/adapters/local-command-retry.ts"],"names":[],"mappings":"AA8CA,MAAM,4BAA4B,GAA2D;IAC3F,WAAW,EAAE;QACX,GAAG,EAAE,aAAa;QAClB,WAAW,EAAE,wBAAwB;QACrC,eAAe,EAAE,kBAAkB;QACnC,WAAW,EAAE,2BAA2B;KACzC;IACD,SAAS,EAAE;QACT,GAAG,EAAE,WAAW;QAChB,WAAW,EAAE,0CAA0C;QACvD,eAAe,EAAE,kBAAkB;QACnC,WAAW,EAAE,2BAA2B;KACzC;IACD,QAAQ,EAAE;QACR,GAAG,EAAE,UAAU;QACf,WAAW,EAAE,qBAAqB;QAClC,eAAe,EAAE,yBAAyB;QAC1C,WAAW,EAAE,iCAAiC;KAC/C;IACD,OAAO,EAAE;QACP,GAAG,EAAE,SAAS;QACd,WAAW,EAAE,mCAAmC;QAChD,eAAe,EAAE,yBAAyB;QAC1C,WAAW,EAAE,iCAAiC;KAC/C;IACD,UAAU,EAAE;QACV,GAAG,EAAE,YAAY;QACjB,WAAW,EAAE,kCAAkC;QAC/C,eAAe,EAAE,yBAAyB;QAC1C,WAAW,EAAE,iCAAiC;KAC/C;IACD,KAAK,EAAE;QACL,GAAG,EAAE,OAAO;QACZ,WAAW,EAAE,6BAA6B;QAC1C,eAAe,EAAE,yBAAyB;QAC1C,WAAW,EAAE,iCAAiC;KAC/C;IACD,IAAI,EAAE;QACJ,GAAG,EAAE,MAAM;QACX,WAAW,EAAE,iCAAiC;QAC9C,eAAe,EAAE,yBAAyB;QAC1C,WAAW,EAAE,iCAAiC;KAC/C;IACD,IAAI,EAAE;QACJ,GAAG,EAAE,MAAM;QACX,WAAW,EAAE,kCAAkC;QAC/C,eAAe,EAAE,yBAAyB;QAC1C,WAAW,EAAE,iCAAiC;KAC/C;IACD,KAAK,EAAE;QACL,GAAG,EAAE,OAAO;QACZ,WAAW,EAAE,sCAAsC;QACnD,eAAe,EAAE,yBAAyB;QAC1C,WAAW,EAAE,iCAAiC;KAC/C;IACD,KAAK,EAAE;QACL,GAAG,EAAE,OAAO;QACZ,WAAW,EAAE,iDAAiD;QAC9D,eAAe,EAAE,yBAAyB;QAC1C,WAAW,EAAE,iCAAiC;KAC/C;IACD,MAAM,EAAE;QACN,GAAG,EAAE,QAAQ;QACb,WAAW,EAAE,6BAA6B;QAC1C,eAAe,EAAE,yBAAyB;QAC1C,WAAW,EAAE,iCAAiC;KAC/C;IACD,IAAI,EAAE;QACJ,GAAG,EAAE,MAAM;QACX,WAAW,EAAE,6CAA6C;QAC1D,eAAe,EAAE,kBAAkB;QACnC,WAAW,EAAE,2BAA2B;KACzC;IACD,aAAa,EAAE;QACb,GAAG,EAAE,eAAe;QACpB,WAAW,EAAE,4CAA4C;QACzD,eAAe,EAAE,kBAAkB;QACnC,WAAW,EAAE,2BAA2B;KACzC;IACD,QAAQ,EAAE;QACR,GAAG,EAAE,UAAU;QACf,WAAW,EAAE,gCAAgC;QAC7C,eAAe,EAAE,OAAO;QACxB,WAAW,EAAE,iCAAiC;KAC/C;IACD,UAAU,EAAE;QACV,GAAG,EAAE,YAAY;QACjB,WAAW,EAAE,8BAA8B;QAC3C,eAAe,EAAE,OAAO;QACxB,WAAW,EAAE,iCAAiC;KAC/C;IACD,QAAQ,EAAE;QACR,GAAG,EAAE,UAAU;QACf,WAAW,EAAE,yCAAyC;QACtD,eAAe,EAAE,kBAAkB;QACnC,WAAW,EAAE,2BAA2B;KACzC;IACD,OAAO,EAAE;QACP,GAAG,EAAE,SAAS;QACd,WAAW,EAAE,mCAAmC;QAChD,eAAe,EAAE,kBAAkB;QACnC,WAAW,EAAE,2BAA2B;KACzC;IACD,MAAM,EAAE;QACN,GAAG,EAAE,QAAQ;QACb,WAAW,EAAE,0BAA0B;QACvC,eAAe,EAAE,yBAAyB;QAC1C,WAAW,EAAE,iCAAiC;KAC/C;IACD,OAAO,EAAE;QACP,GAAG,EAAE,SAAS;QACd,WAAW,EAAE,uBAAuB;QACpC,eAAe,EAAE,kBAAkB;QACnC,WAAW,EAAE,2BAA2B;KACzC;IACD,SAAS,EAAE;QACT,GAAG,EAAE,WAAW;QAChB,WAAW,EAAE,yBAAyB;QACtC,eAAe,EAAE,kBAAkB;QACnC,WAAW,EAAE,2BAA2B;KACzC;IACD,QAAQ,EAAE;QACR,GAAG,EAAE,UAAU;QACf,WAAW,EAAE,4BAA4B;QACzC,eAAe,EAAE,kBAAkB;QACnC,WAAW,EAAE,2BAA2B;KACzC;IACD,aAAa,EAAE;QACb,GAAG,EAAE,eAAe;QACpB,WAAW,EAAE,kCAAkC;QAC/C,eAAe,EAAE,yBAAyB;QAC1C,WAAW,EAAE,iCAAiC;KAC/C;IACD,gBAAgB,EAAE;QAChB,GAAG,EAAE,kBAAkB;QACvB,WAAW,EAAE,yBAAyB;QACtC,eAAe,EAAE,kBAAkB;QACnC,WAAW,EAAE,2BAA2B;KACzC;IACD,gBAAgB,EAAE;QAChB,GAAG,EAAE,kBAAkB;QACvB,WAAW,EAAE,yBAAyB;QACtC,eAAe,EAAE,kBAAkB;QACnC,WAAW,EAAE,2BAA2B;KACzC;IACD,UAAU,EAAE;QACV,GAAG,EAAE,YAAY;QACjB,WAAW,EAAE,qCAAqC;QAClD,eAAe,EAAE,yBAAyB;QAC1C,WAAW,EAAE,iCAAiC;KAC/C;IACD,OAAO,EAAE;QACP,GAAG,EAAE,SAAS;QACd,WAAW,EAAE,8BAA8B;QAC3C,eAAe,EAAE,OAAO;QACxB,WAAW,EAAE,iCAAiC;KAC/C;CACF,CAAC;AAEF,MAAM,UAAU,mCAAmC,CACjD,IAAY,EACZ,MAAc;IAEd,MAAM,gBAAgB,GAAG,MAAM,CAAC,WAAW,EAAE,CAAC;IAC9C,IAAI,gBAAgB,KAAK,KAAK,IAAI,IAAI,KAAK,OAAO,EAAE,CAAC;QACnD,OAAO,4BAA4B,CAAC,SAAS,CAAC;IAChD,CAAC;IACD,IAAI,gBAAgB,KAAK,KAAK,IAAI,qBAAqB,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC;QACnE,OAAO,4BAA4B,CAAC,WAAW,CAAC;IAClD,CAAC;IAED,MAAM,WAAW,GAAG,IAAI,CAAC,KAAK,CAAC,gCAAgC,CAAC,CAAC;IACjE,MAAM,MAAM,GAAG,WAAW,EAAE,CAAC,CAAC,CAAC,CAAC;IAChC,QAAQ,MAAM,EAAE,CAAC;QACf,KAAK,UAAU;YACb,OAAO,4BAA4B,CAAC,QAAQ,CAAC;QAC/C,KAAK,SAAS;YACZ,OAAO,4BAA4B,CAAC,OAAO,CAAC;QAC9C,KAAK,YAAY;YACf,OAAO,4BAA4B,CAAC,UAAU,CAAC;QACjD,KAAK,OAAO;YACV,OAAO,4BAA4B,CAAC,KAAK,CAAC;QAC5C,KAAK,MAAM;YACT,OAAO,4BAA4B,CAAC,IAAI,CAAC;QAC3C,KAAK,MAAM;YACT,OAAO,4BAA4B,CAAC,IAAI,CAAC;QAC3C,KAAK,OAAO;YACV,OAAO,4BAA4B,CAAC,KAAK,CAAC;QAC5C,KAAK,OAAO;YACV,OAAO,4BAA4B,CAAC,KAAK,CAAC;QAC5C,KAAK,QAAQ;YACX,OAAO,4BAA4B,CAAC,MAAM,CAAC;QAC7C,KAAK,MAAM;YACT,OAAO,4BAA4B,CAAC,IAAI,CAAC;QAC3C,KAAK,eAAe;YAClB,OAAO,4BAA4B,CAAC,aAAa,CAAC;QACpD,KAAK,UAAU;YACb,OAAO,4BAA4B,CAAC,QAAQ,CAAC;QAC/C,KAAK,YAAY;YACf,OAAO,4BAA4B,CAAC,UAAU,CAAC;QACjD,KAAK,UAAU;YACb,OAAO,4BAA4B,CAAC,QAAQ,CAAC;QAC/C,KAAK,SAAS;YACZ,OAAO,4BAA4B,CAAC,OAAO,CAAC;QAC9C,KAAK,QAAQ;YACX,OAAO,4BAA4B,CAAC,MAAM,CAAC;QAC7C,KAAK,KAAK;YACR,OAAO,4BAA4B,CAAC,OAAO,CAAC;QAC9C,KAAK,OAAO;YACV,OAAO,4BAA4B,CAAC,SAAS,CAAC;QAChD,KAAK,MAAM;YACT,OAAO,4BAA4B,CAAC,QAAQ,CAAC;QAC/C,KAAK,QAAQ;YACX,OAAO,4BAA4B,CAAC,aAAa,CAAC;QACpD,KAAK,SAAS;YACZ,OAAO,4BAA4B,CAAC,gBAAgB,CAAC;QACvD,KAAK,SAAS;YACZ,OAAO,4BAA4B,CAAC,gBAAgB,CAAC;QACvD,KAAK,YAAY;YACf,OAAO,4BAA4B,CAAC,UAAU,CAAC;QACjD;YACE,OAAO,4BAA4B,CAAC,OAAO,CAAC;IAChD,CAAC;AACH,CAAC;AAED,MAAM,UAAU,8BAA8B,CAAC,OAAiC;IAC9E,OAAO,CACL,OAAO,CAAC,eAAe,KAAK,kBAAkB;WAC3C,OAAO,CAAC,WAAW,KAAK,2BAA2B,CACvD,CAAC;AACJ,CAAC"}
|
|
@@ -0,0 +1,136 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Local adapter — routes browser actions to the native host HTTP API
|
|
3
|
+
* (localhost:PORT/sessions/:tabId/*). No API key required; uses the
|
|
4
|
+
* active tabId stored by `thinkrun attach`.
|
|
5
|
+
*/
|
|
6
|
+
import type { BrowserAdapter } from './types.js';
|
|
7
|
+
import type { Session, SessionOptions, ActionResult, NavigateOptions, ClickOptions, TypeOptions, ScreenshotOptions, ExtractOptions, WaitOptions, DialogResult, ConsoleResult, NetworkResult } from '../types.js';
|
|
8
|
+
import { readBridgePort } from '../utils.js';
|
|
9
|
+
import type { BlockedOutcome } from '../protected-flow/types.js';
|
|
10
|
+
/** Actionable hint for native host error codes (TTY tips and JSON `hint` field). */
|
|
11
|
+
export declare function getNativeCodeHint(code: string | undefined): string | undefined;
|
|
12
|
+
export declare class LocalAdapter implements BrowserAdapter {
|
|
13
|
+
private baseUrl;
|
|
14
|
+
private defaultTimeout;
|
|
15
|
+
private validatedTabCache;
|
|
16
|
+
private readonly TAB_CACHE_TTL_MS;
|
|
17
|
+
/** Injected fetch function — allows unit tests to intercept all HTTP calls. */
|
|
18
|
+
private readonly fetchFn;
|
|
19
|
+
/**
|
|
20
|
+
* When set (via --tab flag or THINKRUN_TAB_ID env), bypasses the global
|
|
21
|
+
* working-location.json entirely. Each command targets this tab directly.
|
|
22
|
+
*/
|
|
23
|
+
private readonly tabOverride;
|
|
24
|
+
private readonly readBridgePortFn;
|
|
25
|
+
private readonly diagnosticsEnabled;
|
|
26
|
+
constructor(port?: number, fetchFn?: typeof fetch, tabOverride?: string, readBridgePortFn?: typeof readBridgePort);
|
|
27
|
+
/** Read the agent session ID from config (set by `thinkrun attach`). */
|
|
28
|
+
private getAgentSessionId;
|
|
29
|
+
private rethrowTabLock;
|
|
30
|
+
/**
|
|
31
|
+
* Fire-and-forget: sync a browser action to the cloud session activity feed.
|
|
32
|
+
* No-op if no cloud sessionId is persisted for the tab (e.g. no API key configured).
|
|
33
|
+
* Never throws, never blocks the caller.
|
|
34
|
+
*/
|
|
35
|
+
private syncAction;
|
|
36
|
+
private refreshBaseUrl;
|
|
37
|
+
private isTransientBridgeError;
|
|
38
|
+
private isPreDispatchBridgeDisconnect;
|
|
39
|
+
private logDiagnostics;
|
|
40
|
+
private probeBridgeHealth;
|
|
41
|
+
private getLiveExtensionDisconnectHint;
|
|
42
|
+
private isRecentDisconnectedState;
|
|
43
|
+
private revalidateExtensionConnection;
|
|
44
|
+
private extractTabIdFromSessionPath;
|
|
45
|
+
private tryRecoverMissingSession;
|
|
46
|
+
private tryRepairMissingMutatingAuthority;
|
|
47
|
+
/**
|
|
48
|
+
* Pre-action check: if this process has a working location set (via `attach`
|
|
49
|
+
* or `new-window`) and the configured active tab has drifted away from it,
|
|
50
|
+
* silently re-switch the bridge to the working-location tab.
|
|
51
|
+
*
|
|
52
|
+
* This prevents "tab stolen by another agent" where a second agent's `attach`
|
|
53
|
+
* changes the bridge's active tab mid-session.
|
|
54
|
+
*/
|
|
55
|
+
private ensureWorkingLocationTab;
|
|
56
|
+
private assertOwnedTab;
|
|
57
|
+
/**
|
|
58
|
+
* Returns the active tab ID, validating it still exists against the native
|
|
59
|
+
* host's /tabs list. Results are cached within this adapter instance's lifetime
|
|
60
|
+
* (a single CLI command invocation). The cache does NOT persist between commands —
|
|
61
|
+
* the CLI starts a new process for each invocation so `validatedTabCache` is always
|
|
62
|
+
* empty at command start. Clears the stored local session if the tab is gone.
|
|
63
|
+
*/
|
|
64
|
+
private getActiveTabId;
|
|
65
|
+
private request;
|
|
66
|
+
/**
|
|
67
|
+
* In local mode this does not start a cloud browser. However, if an API
|
|
68
|
+
* key is configured the session is registered in the cloud activity feed
|
|
69
|
+
* so screenshots and actions appear alongside cloud/extension sessions.
|
|
70
|
+
* Without an API key this is a silent no-op (no error).
|
|
71
|
+
*/
|
|
72
|
+
startSession(_options?: SessionOptions): Promise<Session>;
|
|
73
|
+
/**
|
|
74
|
+
* In local mode this does not stop a cloud browser. If a session was
|
|
75
|
+
* registered via startSession(), a fire-and-forget local-close request
|
|
76
|
+
* is sent to mark it completed in the activity feed.
|
|
77
|
+
*/
|
|
78
|
+
stopSession(_sessionId?: string): Promise<void>;
|
|
79
|
+
getSession(sessionId: string): Promise<Session>;
|
|
80
|
+
listSessions(): Promise<Session[]>;
|
|
81
|
+
waitForSessionReady(sessionId: string, _timeout?: number): Promise<Session>;
|
|
82
|
+
navigate(url: string, options?: NavigateOptions): Promise<ActionResult>;
|
|
83
|
+
goBack(): Promise<ActionResult>;
|
|
84
|
+
goForward(): Promise<ActionResult>;
|
|
85
|
+
/** Evaluate function suitable for captureFingerprint / classifyElementFailure. */
|
|
86
|
+
private evaluateForFingerprint;
|
|
87
|
+
/** Capture fingerprint with a 3s timeout to avoid blocking the primary action. */
|
|
88
|
+
private tryCaptureFP;
|
|
89
|
+
/** A fingerprint with empty url means capture failed — skip comparison. */
|
|
90
|
+
private static isFingerprintValid;
|
|
91
|
+
/**
|
|
92
|
+
* Enrich an ELEMENT_NOT_FOUND ApiError with obstacle classification.
|
|
93
|
+
* Runs classifyElementFailure to determine WHY the selector failed,
|
|
94
|
+
* then attaches the result as `obstacleType` on the error object.
|
|
95
|
+
* If classification itself fails, returns the original error unchanged.
|
|
96
|
+
*/
|
|
97
|
+
private enrichElementNotFound;
|
|
98
|
+
click(selector: string, options?: ClickOptions): Promise<ActionResult & {
|
|
99
|
+
data?: BlockedOutcome;
|
|
100
|
+
}>;
|
|
101
|
+
type(selector: string, text: string, options?: TypeOptions): Promise<ActionResult & {
|
|
102
|
+
data?: BlockedOutcome;
|
|
103
|
+
}>;
|
|
104
|
+
fill(selector: string, value: string): Promise<ActionResult & {
|
|
105
|
+
data?: BlockedOutcome;
|
|
106
|
+
}>;
|
|
107
|
+
press(key: string): Promise<ActionResult>;
|
|
108
|
+
scroll(options: {
|
|
109
|
+
selector?: string;
|
|
110
|
+
x?: number;
|
|
111
|
+
y?: number;
|
|
112
|
+
}): Promise<ActionResult>;
|
|
113
|
+
hover(selector: string): Promise<ActionResult>;
|
|
114
|
+
select(selector: string, value: string): Promise<ActionResult & {
|
|
115
|
+
data?: BlockedOutcome;
|
|
116
|
+
}>;
|
|
117
|
+
wait(condition: string | number, options?: WaitOptions): Promise<ActionResult>;
|
|
118
|
+
waitForText(text: string, options?: {
|
|
119
|
+
timeout?: number;
|
|
120
|
+
}): Promise<ActionResult>;
|
|
121
|
+
snapshot(): Promise<ActionResult>;
|
|
122
|
+
screenshot(options?: ScreenshotOptions): Promise<ActionResult>;
|
|
123
|
+
extract(selector: string, options?: ExtractOptions): Promise<ActionResult>;
|
|
124
|
+
evaluate(script: string, args?: any[], evalOpts?: {
|
|
125
|
+
timeout?: number;
|
|
126
|
+
}): Promise<ActionResult>;
|
|
127
|
+
getUrl(): Promise<ActionResult>;
|
|
128
|
+
getTitle(): Promise<ActionResult>;
|
|
129
|
+
getHtml(): Promise<ActionResult>;
|
|
130
|
+
getDialog(): Promise<DialogResult>;
|
|
131
|
+
handleDialog(action: 'accept' | 'dismiss', promptText?: string): Promise<ActionResult>;
|
|
132
|
+
getConsoleMessages(): Promise<ConsoleResult>;
|
|
133
|
+
getNetworkRequests(): Promise<NetworkResult>;
|
|
134
|
+
clearLogs(): Promise<ActionResult>;
|
|
135
|
+
}
|
|
136
|
+
//# sourceMappingURL=local.d.ts.map
|