@reticlehq/server 3.3.0 → 3.5.0
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/LICENSE-ENTERPRISE +1 -1
- package/README.md +3 -3
- package/SKILL.md +12 -14
- package/dist/chromium-launch-options.d.ts +4 -3
- package/dist/chromium-launch-options.js +6 -2
- package/dist/command/cli/adhoc-suite.d.ts +22 -0
- package/dist/command/cli/adhoc-suite.js +90 -19
- package/dist/command/cli/adhoc-verdict.d.ts +35 -0
- package/dist/command/cli/adhoc-verdict.js +90 -3
- package/dist/command/cli/answers/gate-hook-message.d.ts +6 -0
- package/dist/command/cli/answers/gate-hook-message.js +6 -0
- package/dist/command/cli/auth/cloud-keystore.d.ts +0 -2
- package/dist/command/cli/auth/cloud-keystore.js +0 -3
- package/dist/command/cli/auth/cloud-session.d.ts +6 -2
- package/dist/command/cli/auth/cloud-session.js +2 -0
- package/dist/command/cli/auth/device-flow.d.ts +2 -2
- package/dist/command/cli/cli-doctor.js +7 -5
- package/dist/command/cli/cli-flow-commands.d.ts +3 -6
- package/dist/command/cli/cli-flow-commands.js +67 -4
- package/dist/command/cli/cli-parse.d.ts +8 -1
- package/dist/command/cli/cli-parse.js +24 -4
- package/dist/command/cli/cli-update-commands.js +8 -1
- package/dist/command/cli/cli-verify.d.ts +24 -3
- package/dist/command/cli/cli-verify.js +54 -11
- package/dist/command/cli/cloud-cli.js +64 -2
- package/dist/command/cli/cloud-kit.js +3 -5
- package/dist/command/cli/cloud-login.d.ts +1 -1
- package/dist/command/cli/cloud-login.js +27 -8
- package/dist/command/cli/demo/demo-page.js +6 -3
- package/dist/command/cli/doctor/browser/chromium-hint.d.ts +5 -0
- package/dist/command/cli/doctor/browser/chromium-hint.js +5 -0
- package/dist/command/cli/launch/cli-launch.d.ts +8 -0
- package/dist/command/cli/launch/cli-launch.js +21 -9
- package/dist/command/cli/launch/sdk-version-match.d.ts +84 -0
- package/dist/command/cli/launch/sdk-version-match.js +206 -0
- package/dist/command/cli/lifecycle/daemon-lifecycle.js +2 -16
- package/dist/command/cli/ports/resolve/cli-port.d.ts +25 -0
- package/dist/command/cli/ports/resolve/cli-port.js +125 -15
- package/dist/command/cli/setup-mcp-cli.js +21 -13
- package/dist/command/cli/tutorial.d.ts +2 -2
- package/dist/command/cli/tutorial.js +21 -7
- package/dist/command/cli.js +79 -11
- package/dist/command/daemon/binding/daemon-status-probe.d.ts +14 -2
- package/dist/command/daemon/binding/daemon-status-probe.js +34 -6
- package/dist/command/daemon/daemon-resolve.d.ts +9 -0
- package/dist/command/daemon/daemon-resolve.js +1 -1
- package/dist/command/daemon/lifetime/daemon-usefulness.d.ts +7 -1
- package/dist/command/daemon/lifetime/daemon-usefulness.js +30 -7
- package/dist/command/dev/stale-issue-guard.d.ts +3 -4
- package/dist/command/dev/stale-issue-guard.js +8 -8
- package/dist/command/setup/bringup/connect-lease.d.ts +17 -0
- package/dist/command/setup/bringup/connect-lease.js +38 -0
- package/dist/command/setup/bringup/dev-server-files.d.ts +68 -0
- package/dist/command/setup/bringup/dev-server-files.js +131 -0
- package/dist/command/setup/bringup/dev-server-log-cap.d.ts +35 -0
- package/dist/command/setup/bringup/dev-server-log-cap.js +121 -0
- package/dist/command/setup/bringup/dev-server-wait.d.ts +2 -0
- package/dist/command/setup/bringup/dev-server-wait.js +1 -1
- package/dist/command/setup/bringup/ensure-daemon.d.ts +65 -4
- package/dist/command/setup/bringup/ensure-daemon.js +135 -16
- package/dist/command/setup/bringup/static-page-server.d.ts +35 -0
- package/dist/command/setup/bringup/static-page-server.js +151 -0
- package/dist/command/setup/desktop-shape.d.ts +4 -0
- package/dist/command/setup/desktop-shape.js +18 -2
- package/dist/command/setup/init/init-port.d.ts +15 -0
- package/dist/command/setup/init/init-port.js +44 -0
- package/dist/command/setup/init/init-runtime.d.ts +1 -1
- package/dist/command/setup/init/init-runtime.js +91 -9
- package/dist/command/setup/node-effects.d.ts +27 -14
- package/dist/command/setup/node-effects.js +86 -45
- package/dist/command/setup/probe/loopback-probe-urls.d.ts +7 -0
- package/dist/command/setup/probe/loopback-probe-urls.js +40 -0
- package/dist/command/setup/probe/page-probe.d.ts +13 -2
- package/dist/command/setup/probe/page-probe.js +18 -3
- package/dist/command/setup/run-setup.d.ts +28 -1
- package/dist/command/setup/run-setup.js +103 -15
- package/dist/command/setup/session-pick.d.ts +13 -0
- package/dist/command/setup/session-pick.js +20 -0
- package/dist/command/setup/setup-command.d.ts +2 -14
- package/dist/command/setup/setup-command.js +105 -31
- package/dist/command/setup/setup-mcp.d.ts +2 -0
- package/dist/command/setup/setup-mcp.js +17 -8
- package/dist/command/setup/terminal/wait-progress.d.ts +8 -0
- package/dist/command/setup/terminal/wait-progress.js +17 -0
- package/dist/command/version/peer-announce.d.ts +6 -2
- package/dist/command/version/peer-announce.js +8 -6
- package/dist/command/version/version-nudge.d.ts +17 -3
- package/dist/command/version/version-nudge.js +25 -4
- package/dist/features/crawl/crawl-empty.js +1 -1
- package/dist/features/crawl/crawl-tools.d.ts +6 -0
- package/dist/features/crawl/crawl-tools.js +57 -0
- package/dist/features/crawl/crawl.js +171 -157
- package/dist/features/exhaust/app-coverage.d.ts +33 -0
- package/dist/features/exhaust/app-coverage.js +31 -0
- package/dist/features/exhaust/code-coverage.d.ts +47 -0
- package/dist/features/exhaust/code-coverage.js +77 -0
- package/dist/features/exhaust/exhaust-run.d.ts +33 -0
- package/dist/features/exhaust/exhaust-run.js +82 -0
- package/dist/features/exhaust/explorer.d.ts +103 -0
- package/dist/features/exhaust/explorer.js +195 -0
- package/dist/features/exhaust/failure-branches.d.ts +33 -0
- package/dist/features/exhaust/failure-branches.js +92 -0
- package/dist/features/exhaust/ledger.d.ts +202 -0
- package/dist/features/exhaust/ledger.js +252 -0
- package/dist/features/exhaust/session-fold.d.ts +31 -0
- package/dist/features/exhaust/session-fold.js +79 -0
- package/dist/features/exhaust/session-port.d.ts +36 -0
- package/dist/features/exhaust/session-port.js +102 -0
- package/dist/features/harness/drive-report.d.ts +0 -9
- package/dist/features/harness/drive-report.js +18 -0
- package/dist/features/harness/driver.js +4 -7
- package/dist/features/harness/fill-values.d.ts +10 -0
- package/dist/features/harness/fill-values.js +50 -11
- package/dist/features/harness/jev-driver.js +30 -13
- package/dist/features/harness/openai-driver.d.ts +12 -0
- package/dist/features/harness/openai-driver.js +21 -12
- package/dist/features/harness/platform-config.js +5 -6
- package/dist/features/license/license.d.ts +2 -2
- package/dist/index.d.ts +9 -0
- package/dist/index.js +56 -19
- package/dist/judgement/capsule/capsule-store.d.ts +4 -4
- package/dist/judgement/domain/domain-model.js +3 -1
- package/dist/judgement/oracles/self-instrument.js +4 -2
- package/dist/judgement/runs/artifact/replay-mapping.d.ts +2 -2
- package/dist/judgement/runs/artifact/replay-mapping.js +44 -9
- package/dist/judgement/runs/verification-sync.d.ts +3 -1
- package/dist/judgement/runs/verification-sync.js +1 -1
- package/dist/language/flows/change/affected.d.ts +9 -0
- package/dist/language/flows/change/affected.js +35 -0
- package/dist/language/flows/change/gate.d.ts +20 -0
- package/dist/language/flows/change/gate.js +12 -1
- package/dist/language/flows/flow-author.d.ts +7 -0
- package/dist/language/flows/flow-author.js +19 -0
- package/dist/language/flows/flow-expect-grammar.js +1 -1
- package/dist/language/flows/flow-journey.d.ts +54 -0
- package/dist/language/flows/flow-journey.js +119 -0
- package/dist/language/flows/flow-replay-run.d.ts +2 -3
- package/dist/language/flows/flow-replay-run.js +13 -47
- package/dist/language/flows/flow-replay.d.ts +22 -8
- package/dist/language/flows/flow-replay.js +55 -9
- package/dist/language/flows/flow-result.d.ts +2 -0
- package/dist/language/flows/flow-result.js +25 -0
- package/dist/language/flows/flow-tools.js +17 -5
- package/dist/language/flows/flows.d.ts +10 -1
- package/dist/language/flows/flows.js +90 -14
- package/dist/language/flows/recording/replay-halt.js +3 -1
- package/dist/language/flows/recording/tape/recordings.d.ts +30 -1
- package/dist/language/flows/recording/tape/recordings.js +55 -1
- package/dist/language/flows/replay.d.ts +19 -0
- package/dist/language/flows/replay.js +42 -6
- package/dist/language/flows/verify-change-tools.js +5 -2
- package/dist/launch-chromium.d.ts +80 -0
- package/dist/launch-chromium.js +218 -0
- package/dist/memory/cloud/cloud-config.d.ts +11 -2
- package/dist/memory/cloud/cloud-config.js +47 -7
- package/dist/memory/cloud/cloud-sync.d.ts +4 -1
- package/dist/memory/cloud/cloud-sync.js +6 -9
- package/dist/memory/cloud/harness-offer.js +5 -6
- package/dist/memory/cloud/harness-switch.js +5 -6
- package/dist/memory/cloud/sync-cycle.d.ts +77 -3
- package/dist/memory/cloud/sync-cycle.js +325 -55
- package/dist/memory/cloud/sync-daemon.js +24 -20
- package/dist/memory/cloud/sync-disk.js +16 -2
- package/dist/memory/intent/intent-shard.d.ts +10 -32
- package/dist/memory/intent/intent-shard.js +0 -10
- package/dist/memory/intent/intent-tools.js +8 -3
- package/dist/memory/journal/drive-flow.d.ts +18 -13
- package/dist/memory/journal/drive-flow.js +45 -37
- package/dist/memory/journal/envelope.d.ts +8 -8
- package/dist/memory/journal/journal-query.d.ts +14 -0
- package/dist/memory/journal/journal-query.js +15 -0
- package/dist/memory/journal/on-disk/workspace-tiers.js +2 -0
- package/dist/memory/journal/session-end.d.ts +9 -1
- package/dist/memory/journal/session-end.js +24 -12
- package/dist/memory/project/artifact-root-resolver.d.ts +10 -0
- package/dist/memory/project/artifact-root-resolver.js +46 -19
- package/dist/memory/project/dir/reticle-dir.d.ts +2 -0
- package/dist/memory/project/dir/reticle-dir.js +1 -0
- package/dist/memory/project/project-tools.js +3 -1
- package/dist/portal/bridge/auth-failure-reason.d.ts +1 -1
- package/dist/portal/bridge/auth-failure-reason.js +4 -2
- package/dist/portal/bridge/bridge.d.ts +12 -3
- package/dist/portal/bridge/bridge.js +49 -3
- package/dist/portal/input/js-coverage.d.ts +25 -0
- package/dist/portal/input/js-coverage.js +30 -0
- package/dist/portal/input/real-input.d.ts +11 -0
- package/dist/portal/input/real-input.js +29 -4
- package/dist/portal/input/viewport-tools.js +16 -6
- package/dist/portal/pool/playwright-launcher.d.ts +6 -0
- package/dist/portal/pool/playwright-launcher.js +20 -13
- package/dist/portal/session/dev-server/dev-command.d.ts +2 -2
- package/dist/portal/session/dev-server/dev-command.js +30 -12
- package/dist/portal/session/dev-server/dev-server-probe.js +17 -1
- package/dist/portal/session/dev-server/route-status-probe.d.ts +24 -0
- package/dist/portal/session/dev-server/route-status-probe.js +57 -0
- package/dist/portal/session/facts/observed-state.d.ts +11 -0
- package/dist/portal/session/facts/observed-state.js +34 -0
- package/dist/portal/session/no-session-diagnosis.d.ts +29 -0
- package/dist/portal/session/no-session-diagnosis.js +62 -5
- package/dist/portal/session/no-session-next-action.d.ts +13 -0
- package/dist/portal/session/no-session-next-action.js +48 -9
- package/dist/portal/session/no-session-watch.d.ts +18 -0
- package/dist/portal/session/no-session-watch.js +88 -2
- package/dist/portal/session/session-health.js +3 -2
- package/dist/portal/session/session-manager.d.ts +20 -6
- package/dist/portal/session/session-manager.js +19 -3
- package/dist/portal/session/session-reaper.d.ts +28 -0
- package/dist/portal/session/session-reaper.js +49 -1
- package/dist/portal/session/session.d.ts +10 -8
- package/dist/portal/session/session.js +24 -32
- package/dist/surface/http-server.d.ts +3 -2
- package/dist/surface/http-server.js +8 -5
- package/dist/surface/mcp/mcp-proxy.d.ts +2 -2
- package/dist/surface/mcp/mcp-proxy.js +2 -2
- package/dist/surface/mcp/mcp.js +5 -3
- package/dist/surface/mcp/proxy/proxy-daemon-probe.d.ts +13 -1
- package/dist/surface/mcp/proxy/proxy-daemon-probe.js +27 -2
- package/dist/surface/mcp/proxy/proxy-log.js +3 -5
- package/dist/surface/mcp/server-instructions.js +9 -7
- package/dist/surface/tools/act/after-match.d.ts +17 -0
- package/dist/surface/tools/act/after-match.js +30 -0
- package/dist/surface/tools/act/durable.d.ts +69 -0
- package/dist/surface/tools/act/durable.js +139 -0
- package/dist/surface/tools/act/navigation/navigate-arrival.d.ts +13 -6
- package/dist/surface/tools/act/navigation/navigate-arrival.js +47 -10
- package/dist/surface/tools/act/navigation/navigate-result.d.ts +1 -12
- package/dist/surface/tools/act/navigation/navigate-result.js +21 -3
- package/dist/surface/tools/act/proved-controls.d.ts +9 -0
- package/dist/surface/tools/act/proved-controls.js +11 -0
- package/dist/surface/tools/act/sequence-grade.d.ts +5 -0
- package/dist/surface/tools/act/sequence-grade.js +32 -1
- package/dist/surface/tools/act-capsule.d.ts +7 -0
- package/dist/surface/tools/act-capsule.js +46 -1
- package/dist/surface/tools/act-sequence-tool.js +25 -8
- package/dist/surface/tools/act-tools.js +28 -52
- package/dist/surface/tools/assert/assert-grade.js +12 -1
- package/dist/surface/tools/assert/assert-verdict.js +2 -2
- package/dist/surface/tools/browser-tools.js +14 -2
- package/dist/surface/tools/coverage-tools.js +27 -1
- package/dist/surface/tools/dynamic-tools.js +29 -2
- package/dist/surface/tools/error-recovery.js +5 -6
- package/dist/surface/tools/feedback-invite.js +6 -4
- package/dist/surface/tools/harness-explore.d.ts +3 -2
- package/dist/surface/tools/harness-explore.js +12 -7
- package/dist/surface/tools/invoke-tool.js +12 -8
- package/dist/surface/tools/lease-tools.js +15 -6
- package/dist/surface/tools/live-call-text.js +4 -1
- package/dist/surface/tools/observe-tools.js +9 -1
- package/dist/surface/tools/tool-kit.d.ts +10 -0
- package/dist/surface/tools/tools.js +4 -0
- package/dist/telemetry/argument-shape.d.ts +0 -2
- package/dist/telemetry/argument-shape.js +1 -5
- package/dist/telemetry/error-class.d.ts +2 -3
- package/dist/telemetry/error-class.js +2 -3
- package/dist/telemetry/harness-drive.d.ts +0 -2
- package/dist/telemetry/harness-drive.js +0 -4
- package/dist/telemetry/onboarding-firsts.d.ts +2 -2
- package/dist/telemetry/onboarding-firsts.js +2 -2
- package/dist/wire-journal.d.ts +3 -0
- package/dist/wire-journal.js +4 -0
- package/dist/workspace-packages.d.ts +0 -2
- package/dist/workspace-packages.js +1 -9
- package/docs/README.md +4 -2
- package/docs/actions.mdx +3 -4
- package/docs/agent-cheatsheet.md +4 -4
- package/docs/architecture.md +6 -6
- package/docs/best-practices.mdx +1 -1
- package/docs/capabilities.mdx +32 -1
- package/docs/cli/cloud.mdx +20 -8
- package/docs/cli/doctor.mdx +4 -0
- package/docs/cli/feedback.mdx +2 -2
- package/docs/cli/gate.mdx +9 -4
- package/docs/cli/update.mdx +10 -0
- package/docs/cli.mdx +22 -7
- package/docs/desktop.mdx +14 -10
- package/docs/environment.mdx +87 -0
- package/docs/faq.mdx +18 -16
- package/docs/first-drive.md +5 -13
- package/docs/flows.md +21 -2
- package/docs/frameworks.mdx +29 -10
- package/docs/getting-started.md +15 -5
- package/docs/http-transport.md +6 -3
- package/docs/human-control.md +2 -2
- package/docs/index.mdx +16 -6
- package/docs/install-agentic.mdx +2 -2
- package/docs/install-manual.mdx +1 -1
- package/docs/integration-patterns.md +3 -3
- package/docs/multi-agent-testing.md +1 -1
- package/docs/packages/babel-plugin.mdx +1 -1
- package/docs/packages/browser.mdx +2 -2
- package/docs/packages/next.mdx +3 -0
- package/docs/packages/react.mdx +2 -2
- package/docs/packages/tauri.mdx +1 -1
- package/docs/packages/vite-plugin.mdx +4 -2
- package/docs/packages.mdx +9 -9
- package/docs/predicates.mdx +50 -5
- package/docs/quickstart.mdx +12 -10
- package/docs/recipes.mdx +2 -2
- package/docs/state-management.mdx +2 -2
- package/docs/system-map.md +1 -1
- package/docs/telemetry.md +1 -1
- package/docs/token-efficiency.md +3 -3
- package/docs/tools/act-and-wait.mdx +1 -0
- package/docs/tools/act-sequence.mdx +1 -1
- package/docs/tools/act.mdx +1 -1
- package/docs/tools/console.mdx +1 -1
- package/docs/tools/inspect.mdx +1 -1
- package/docs/tools/network.mdx +1 -1
- package/docs/tools/query.mdx +1 -1
- package/docs/tools/sessions.mdx +1 -1
- package/docs/tools/snapshot.mdx +1 -1
- package/docs/tools/state.mdx +1 -1
- package/docs/tools/wait-for.mdx +1 -1
- package/docs/usage.md +7 -7
- package/docs/use-cases.mdx +157 -0
- package/docs/vs-screenshots.mdx +3 -3
- package/docs/what-is-recorded.md +2 -2
- package/docs/what-is-reticle.mdx +17 -20
- package/docs/why-reticle.mdx +14 -21
- package/package.json +10 -9
- package/dist/judgement/capsule/minimize.d.ts +0 -12
- package/dist/judgement/capsule/minimize.js +0 -22
- package/dist/judgement/phenomena/phenomena.d.ts +0 -27
- package/dist/judgement/phenomena/phenomena.js +0 -101
- package/dist/language/flows/flow-report.d.ts +0 -22
- package/dist/language/flows/flow-report.js +0 -106
|
@@ -41,3 +41,20 @@ export function waitProgressLine(elapsedMs, watching, lastSpokeAtMs) {
|
|
|
41
41
|
return (`Waiting ${seconds} for the dev server — watching ${watching}. If the app is already up ` +
|
|
42
42
|
`somewhere else, that url is the thing to check first.`);
|
|
43
43
|
}
|
|
44
|
+
/**
|
|
45
|
+
* The same, for the wait on a session after the app is up.
|
|
46
|
+
*
|
|
47
|
+
* That wait was silent as well: a desktop init printed "Waiting for the app to launch and dial in."
|
|
48
|
+
* and then nothing for the whole of its budget. Naming what is awaited and how long remains is what
|
|
49
|
+
* lets somebody tell a slow start from a wedged one — and when to stop waiting themselves.
|
|
50
|
+
*/
|
|
51
|
+
export function connectProgressLine(elapsedMs, lastSpokeAtMs, budgetMs, awaiting) {
|
|
52
|
+
if (elapsedMs < WAIT_PROGRESS_EVERY_MS)
|
|
53
|
+
return undefined;
|
|
54
|
+
if (lastSpokeAtMs !== undefined && elapsedMs - lastSpokeAtMs < WAIT_PROGRESS_EVERY_MS) {
|
|
55
|
+
return undefined;
|
|
56
|
+
}
|
|
57
|
+
const seconds = (ms) => `${String(Math.max(0, Math.floor(ms / 1000)))}s`;
|
|
58
|
+
return (`Still waiting for ${awaiting} to connect: ${seconds(elapsedMs)} so far, giving up in ` +
|
|
59
|
+
`${seconds(budgetMs - elapsedMs)}.`);
|
|
60
|
+
}
|
|
@@ -1,4 +1,8 @@
|
|
|
1
1
|
export declare const PEER_VERSION_PARAM = "peerVersion";
|
|
2
2
|
export declare const PEER_CONTRACT_PARAM = "peerContract";
|
|
3
|
-
/**
|
|
4
|
-
|
|
3
|
+
/**
|
|
4
|
+
* Compare an attaching agent process against this daemon: the skew to tell THAT connection, or
|
|
5
|
+
* undefined when they agree. Returned rather than queued daemon-wide, because it is true only for the
|
|
6
|
+
* agent that announced it (#1136).
|
|
7
|
+
*/
|
|
8
|
+
export declare function agentPeerSkew(version: string | null, contract: string | null): string | undefined;
|
|
@@ -13,12 +13,15 @@
|
|
|
13
13
|
*/
|
|
14
14
|
import { CONTRACT_FINGERPRINT } from '@reticlehq/core';
|
|
15
15
|
import { SERVER_VERSION } from './identity/server-version.js';
|
|
16
|
-
import { daemonFix, describeSkew
|
|
17
|
-
import { noteVersionSkew } from './version-nudge.js';
|
|
16
|
+
import { daemonFix, describeSkew } from './version-skew.js';
|
|
18
17
|
export const PEER_VERSION_PARAM = 'peerVersion';
|
|
19
18
|
export const PEER_CONTRACT_PARAM = 'peerContract';
|
|
20
|
-
/**
|
|
21
|
-
|
|
19
|
+
/**
|
|
20
|
+
* Compare an attaching agent process against this daemon: the skew to tell THAT connection, or
|
|
21
|
+
* undefined when they agree. Returned rather than queued daemon-wide, because it is true only for the
|
|
22
|
+
* agent that announced it (#1136).
|
|
23
|
+
*/
|
|
24
|
+
export function agentPeerSkew(version, contract) {
|
|
22
25
|
const skew = describeSkew({
|
|
23
26
|
what: "the agent's MCP server",
|
|
24
27
|
version: version ?? undefined,
|
|
@@ -27,6 +30,5 @@ export function noteAgentPeer(version, contract) {
|
|
|
27
30
|
// MCP server, so the daemon is the newer half whenever the announcing agent is behind.
|
|
28
31
|
fix: daemonFix(SERVER_VERSION, version ?? undefined),
|
|
29
32
|
}, { version: SERVER_VERSION, contract: CONTRACT_FINGERPRINT });
|
|
30
|
-
|
|
31
|
-
noteVersionSkew(SkewPair.DAEMON, skew);
|
|
33
|
+
return skew;
|
|
32
34
|
}
|
|
@@ -11,7 +11,7 @@
|
|
|
11
11
|
* result, then goes quiet until the skew CHANGES. Told, not nagged: a banner on every call is one an
|
|
12
12
|
* agent learns to skip, and it would cost those tokens on every call for the rest of the session.
|
|
13
13
|
*/
|
|
14
|
-
import
|
|
14
|
+
import { SkewPair } from './version-skew.js';
|
|
15
15
|
interface VersionSkewNudge {
|
|
16
16
|
pair: SkewPair;
|
|
17
17
|
action: string;
|
|
@@ -21,8 +21,20 @@ interface VersionSkewNudge {
|
|
|
21
21
|
* a second tab on a third version is news; the same tab reconnecting is not.
|
|
22
22
|
*/
|
|
23
23
|
export declare function noteVersionSkew(pair: SkewPair, action: string): void;
|
|
24
|
-
/**
|
|
25
|
-
|
|
24
|
+
/**
|
|
25
|
+
* A daemon skew bound to the one MCP connection whose server announced it, told once (#1136).
|
|
26
|
+
*
|
|
27
|
+
* The page pair stays in the daemon-wide queue: it is a fact about a tab, true for whoever asks.
|
|
28
|
+
* This pair is a fact about the CALLER, and telling it to a different caller is advice to restart
|
|
29
|
+
* a server that is fine, or to run `reticle stop` and cut every agent on the daemon.
|
|
30
|
+
*/
|
|
31
|
+
export declare function connectionSkew(action: string): {
|
|
32
|
+
take(): string | undefined;
|
|
33
|
+
};
|
|
34
|
+
/** The next undelivered skew, once: this connection's own first, then the daemon-wide queue. */
|
|
35
|
+
export declare function takeVersionSkew(connection?: {
|
|
36
|
+
take(): string | undefined;
|
|
37
|
+
}): VersionSkewNudge | undefined;
|
|
26
38
|
/**
|
|
27
39
|
* Splice pending skew onto a tool-error payload.
|
|
28
40
|
*
|
|
@@ -36,6 +48,8 @@ export declare function takeVersionSkewOnto(payload: {
|
|
|
36
48
|
error: string;
|
|
37
49
|
recovery?: string;
|
|
38
50
|
feedback?: string;
|
|
51
|
+
}, connection?: {
|
|
52
|
+
take(): string | undefined;
|
|
39
53
|
}): Record<string, unknown>;
|
|
40
54
|
/** Tests only — drop the module state so each case starts clean. */
|
|
41
55
|
export declare function resetVersionSkew(): void;
|
|
@@ -12,6 +12,7 @@
|
|
|
12
12
|
* agent learns to skip, and it would cost those tokens on every call for the rest of the session.
|
|
13
13
|
*/
|
|
14
14
|
import { EnvelopeKey } from '../../surface/tools/tool-kit.js';
|
|
15
|
+
import { SkewPair } from './version-skew.js';
|
|
15
16
|
/** Pending per pair — the SDK and the daemon are different upgrades and each is worth saying once. */
|
|
16
17
|
const pending = new Map();
|
|
17
18
|
/** The last message delivered for each pair, so the same skew is never repeated. */
|
|
@@ -25,8 +26,28 @@ export function noteVersionSkew(pair, action) {
|
|
|
25
26
|
return;
|
|
26
27
|
pending.set(pair, action);
|
|
27
28
|
}
|
|
28
|
-
/**
|
|
29
|
-
|
|
29
|
+
/**
|
|
30
|
+
* A daemon skew bound to the one MCP connection whose server announced it, told once (#1136).
|
|
31
|
+
*
|
|
32
|
+
* The page pair stays in the daemon-wide queue: it is a fact about a tab, true for whoever asks.
|
|
33
|
+
* This pair is a fact about the CALLER, and telling it to a different caller is advice to restart
|
|
34
|
+
* a server that is fine, or to run `reticle stop` and cut every agent on the daemon.
|
|
35
|
+
*/
|
|
36
|
+
export function connectionSkew(action) {
|
|
37
|
+
let pendingAction = action;
|
|
38
|
+
return {
|
|
39
|
+
take: () => {
|
|
40
|
+
const taken = pendingAction;
|
|
41
|
+
pendingAction = undefined;
|
|
42
|
+
return taken;
|
|
43
|
+
},
|
|
44
|
+
};
|
|
45
|
+
}
|
|
46
|
+
/** The next undelivered skew, once: this connection's own first, then the daemon-wide queue. */
|
|
47
|
+
export function takeVersionSkew(connection) {
|
|
48
|
+
const own = connection?.take();
|
|
49
|
+
if (own !== undefined)
|
|
50
|
+
return { pair: SkewPair.DAEMON, action: own };
|
|
30
51
|
for (const [pair, action] of pending) {
|
|
31
52
|
pending.delete(pair);
|
|
32
53
|
delivered.set(pair, action);
|
|
@@ -43,8 +64,8 @@ export function takeVersionSkew() {
|
|
|
43
64
|
* feedback ask is replaced: the skew IS the next move, and inviting a bug report about it is
|
|
44
65
|
* backwards. A recognized recovery is kept; the envelope still rides along.
|
|
45
66
|
*/
|
|
46
|
-
export function takeVersionSkewOnto(payload) {
|
|
47
|
-
const skew = takeVersionSkew();
|
|
67
|
+
export function takeVersionSkewOnto(payload, connection) {
|
|
68
|
+
const skew = takeVersionSkew(connection);
|
|
48
69
|
if (skew === undefined)
|
|
49
70
|
return payload;
|
|
50
71
|
const { feedback, ...rest } = payload;
|
|
@@ -19,6 +19,6 @@ export function crawlEmptyNote(outcome) {
|
|
|
19
19
|
return `no interactive controls were found on this page, so nothing was clicked — the crawl ran and found none, which is a result rather than a failure.${capped}`;
|
|
20
20
|
}
|
|
21
21
|
return (`${String(outcome.interactiveFound)} interactive controls were found and none of them were clicked. ` +
|
|
22
|
-
`That is not an empty page, so something stopped the loop — report it with
|
|
22
|
+
`That is not an empty page, so something stopped the loop — report it with reticle_session { action: "feedback" }, ` +
|
|
23
23
|
`including this page's URL and one control's ref.`);
|
|
24
24
|
}
|
|
@@ -1,4 +1,10 @@
|
|
|
1
1
|
import type { ToolDef } from '../../surface/tools/tool-kit.js';
|
|
2
|
+
/**
|
|
3
|
+
* The configured secret for a field, only on the origin the crawl started on. The field name comes
|
|
4
|
+
* from whatever page is on screen, so without the check a page on another origin could name an
|
|
5
|
+
* empty textbox after a secret and have the crawl type it in.
|
|
6
|
+
*/
|
|
7
|
+
export declare function crawlSecret(startUrl: string, env: Readonly<Record<string, string | undefined>>): (name: string, pageUrl: string) => string | undefined;
|
|
2
8
|
/**
|
|
3
9
|
* The autonomous "smart monkey" tool. Builds on reticle_explore (which only LISTS) by
|
|
4
10
|
* actually clicking each reachable control and classifying the reaction. DESTRUCTIVE by nature —
|
|
@@ -5,8 +5,29 @@ import { ReticleTool } from '@reticlehq/core';
|
|
|
5
5
|
import { asNumber, asString } from '@reticlehq/core';
|
|
6
6
|
import { stepCountSchema, timeoutMsSchema } from '../../surface/tools/args/numeric-bounds.js';
|
|
7
7
|
import { crawl } from './crawl.js';
|
|
8
|
+
import { EXHAUST_DEFAULT_ACTIONS, runExhaustive } from '../exhaust/exhaust-run.js';
|
|
9
|
+
import { heuristicFillValue } from '../harness/fill-values.js';
|
|
10
|
+
import { secretEnvKey } from '../../language/flows/flows.js';
|
|
11
|
+
import { CRAWL_DEFAULTS } from '@reticlehq/core';
|
|
8
12
|
import { routeFromUrl, routesFromEvents } from '../../memory/project/learned-routes.js';
|
|
9
13
|
const nodeSleep = (ms) => new Promise((resolve) => setTimeout(resolve, ms));
|
|
14
|
+
/**
|
|
15
|
+
* The configured secret for a field, only on the origin the crawl started on. The field name comes
|
|
16
|
+
* from whatever page is on screen, so without the check a page on another origin could name an
|
|
17
|
+
* empty textbox after a secret and have the crawl type it in.
|
|
18
|
+
*/
|
|
19
|
+
export function crawlSecret(startUrl, env) {
|
|
20
|
+
const originOf = (url) => {
|
|
21
|
+
try {
|
|
22
|
+
return new URL(url).origin;
|
|
23
|
+
}
|
|
24
|
+
catch {
|
|
25
|
+
return undefined;
|
|
26
|
+
}
|
|
27
|
+
};
|
|
28
|
+
const home = originOf(startUrl);
|
|
29
|
+
return (name, pageUrl) => home !== undefined && home === originOf(pageUrl) ? env[secretEnvKey(name)] : undefined;
|
|
30
|
+
}
|
|
10
31
|
/**
|
|
11
32
|
* The autonomous "smart monkey" tool. Builds on reticle_explore (which only LISTS) by
|
|
12
33
|
* actually clicking each reachable control and classifying the reaction. DESTRUCTIVE by nature —
|
|
@@ -27,6 +48,10 @@ export const CRAWL_TOOLS = [
|
|
|
27
48
|
.string()
|
|
28
49
|
.optional()
|
|
29
50
|
.describe('CSS selector or element ref to restrict crawling to a subtree.'),
|
|
51
|
+
exhaustive: z
|
|
52
|
+
.boolean()
|
|
53
|
+
.optional()
|
|
54
|
+
.describe("Walk every state it can tell apart, drive each write's failure path, fold into the coverage ledger."),
|
|
30
55
|
confirmDangerous: z
|
|
31
56
|
.boolean()
|
|
32
57
|
.optional()
|
|
@@ -62,6 +87,8 @@ export const CRAWL_TOOLS = [
|
|
|
62
87
|
.optional()
|
|
63
88
|
.describe('Present only when the page exceeded one snapshot, so controls past the cap were never listed. When present, a zero-anomaly result does NOT mean the app is clean.'),
|
|
64
89
|
truncated: z.boolean(),
|
|
90
|
+
// Only on `exhaustive` — see features/exhaust/exhaust-run.ts. Loose: it carries the levels.
|
|
91
|
+
exhaustive: z.record(z.unknown()).optional(),
|
|
65
92
|
},
|
|
66
93
|
handler: async (deps, args) => {
|
|
67
94
|
const session = deps.sessions.resolve(asString(args['sessionId']));
|
|
@@ -76,6 +103,36 @@ export const CRAWL_TOOLS = [
|
|
|
76
103
|
...(scope !== undefined ? { scope } : {}),
|
|
77
104
|
...(true === args['confirmDangerous'] ? { confirmDangerous: true } : {}),
|
|
78
105
|
};
|
|
106
|
+
if (true === args['exhaustive']) {
|
|
107
|
+
// Starts code-coverage collection, so the drive below is measured. See takeCodeCoverage.
|
|
108
|
+
await deps.realInput?.takeCodeCoverage?.(session.url);
|
|
109
|
+
const secret = crawlSecret(session.url, process.env);
|
|
110
|
+
return runExhaustive({
|
|
111
|
+
sessions: deps.sessions,
|
|
112
|
+
session,
|
|
113
|
+
startUrl: session.url,
|
|
114
|
+
maxActions: maxSteps ?? EXHAUST_DEFAULT_ACTIONS,
|
|
115
|
+
settleMs: settleMs ?? CRAWL_DEFAULTS.SETTLE_MS,
|
|
116
|
+
fillValue: (label, pageUrl) => {
|
|
117
|
+
const name = /"([^"]*)"/.exec(label)?.[1] ?? label;
|
|
118
|
+
return secret(name, pageUrl) ?? heuristicFillValue(name);
|
|
119
|
+
},
|
|
120
|
+
now: deps.now,
|
|
121
|
+
sleep: nodeSleep,
|
|
122
|
+
...(deps.realInput?.setMocks === undefined
|
|
123
|
+
? {}
|
|
124
|
+
: {
|
|
125
|
+
setMocks: (url, rules) => deps.realInput?.setMocks?.(url, rules) ?? Promise.resolve(false),
|
|
126
|
+
}),
|
|
127
|
+
...(deps.realInput?.takeCodeCoverage === undefined
|
|
128
|
+
? {}
|
|
129
|
+
: {
|
|
130
|
+
takeCode: (url) => deps.realInput?.takeCodeCoverage?.(url) ?? Promise.resolve(undefined),
|
|
131
|
+
}),
|
|
132
|
+
fs: deps.fs,
|
|
133
|
+
reticleRoot: sessionRoot(deps, session.id),
|
|
134
|
+
});
|
|
135
|
+
}
|
|
79
136
|
const report = await crawl(session, opts, nodeSleep);
|
|
80
137
|
const routes = [
|
|
81
138
|
...(initialRoute === undefined ? [] : [initialRoute]),
|