@reticlehq/server 3.8.2 → 3.10.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 +201 -104
- package/NOTICE +5 -0
- package/README.md +1 -1
- package/SKILL.md +13 -12
- package/bin/launch.js +13 -0
- package/bin/package.json +3 -0
- package/bin/reticle.js +66 -8
- package/dist/chromium-launch-options.d.ts +25 -0
- package/dist/chromium-launch-options.js +21 -1
- package/dist/command/cli/adhoc-suite.js +2 -0
- package/dist/command/cli/adhoc-verdict.d.ts +2 -43
- package/dist/command/cli/adhoc-verdict.js +50 -160
- package/dist/command/cli/answers/gate-exit.d.ts +6 -2
- package/dist/command/cli/answers/gate-exit.js +12 -2
- package/dist/command/cli/answers/mcp-connection-hint.d.ts +2 -0
- package/dist/command/cli/answers/mcp-connection-hint.js +6 -0
- package/dist/command/cli/ci-hint.d.ts +44 -0
- package/dist/command/cli/ci-hint.js +72 -0
- package/dist/command/cli/cli-doctor.d.ts +6 -1
- package/dist/command/cli/cli-doctor.js +46 -5
- package/dist/command/cli/cli-flow-commands.d.ts +7 -1
- package/dist/command/cli/cli-flow-commands.js +39 -24
- package/dist/command/cli/cli-kill.d.ts +21 -0
- package/dist/command/cli/cli-kill.js +47 -4
- package/dist/command/cli/cli-parse-compare.d.ts +22 -0
- package/dist/command/cli/cli-parse-compare.js +75 -0
- package/dist/command/cli/cli-parse-grade.d.ts +36 -0
- package/dist/command/cli/cli-parse-grade.js +75 -0
- package/dist/command/cli/cli-parse-grammar.d.ts +2 -0
- package/dist/command/cli/cli-parse-grammar.js +18 -20
- package/dist/command/cli/cli-parse-verify.d.ts +10 -0
- package/dist/command/cli/cli-parse-verify.js +63 -14
- package/dist/command/cli/cli-parse.d.ts +22 -17
- package/dist/command/cli/cli-parse.js +54 -32
- package/dist/command/cli/cli-update-commands.d.ts +1 -1
- package/dist/command/cli/cli-update-commands.js +29 -20
- package/dist/command/cli/cli-usage.js +61 -31
- package/dist/command/cli/cli-verify.d.ts +17 -3
- package/dist/command/cli/cli-verify.js +59 -21
- package/dist/command/cli/cloud-cli.js +2 -119
- package/dist/command/cli/daemon-link/daemon-client.d.ts +45 -0
- package/dist/command/cli/daemon-link/daemon-client.js +205 -0
- package/dist/command/cli/doctor/browser/chromium-hint.d.ts +6 -1
- package/dist/command/cli/doctor/browser/chromium-hint.js +11 -5
- package/dist/command/cli/doctor/doctor-daemon-line.js +6 -3
- package/dist/command/cli/doctor/doctor-fix.d.ts +44 -0
- package/dist/command/cli/doctor/doctor-fix.js +89 -0
- package/dist/command/cli/doctor/doctor-launcher-line.d.ts +23 -0
- package/dist/command/cli/doctor/doctor-launcher-line.js +60 -0
- package/dist/command/cli/doctor/doctor-rows.d.ts +4 -0
- package/dist/command/cli/doctor/doctor-rows.js +4 -0
- package/dist/command/cli/doctor-repairs.d.ts +64 -0
- package/dist/command/cli/doctor-repairs.js +214 -0
- package/dist/command/cli/drive/drive-command.js +3 -7
- package/dist/command/cli/ensure-daemon.d.ts +26 -0
- package/dist/command/cli/ensure-daemon.js +57 -0
- package/dist/command/cli/finished-run/grade-command.d.ts +23 -0
- package/dist/command/cli/finished-run/grade-command.js +180 -0
- package/dist/command/cli/first-use-checks.d.ts +41 -0
- package/dist/command/cli/first-use-checks.js +127 -0
- package/dist/command/cli/first-verdict-node.d.ts +3 -0
- package/dist/command/cli/first-verdict-node.js +189 -0
- package/dist/command/cli/first-verdict.d.ts +126 -0
- package/dist/command/cli/first-verdict.js +267 -0
- package/dist/command/cli/launch/sdk-version-match.d.ts +3 -2
- package/dist/command/cli/launch/sdk-version-match.js +3 -2
- package/dist/command/cli/lifecycle/daemon-lifecycle.d.ts +1 -1
- package/dist/command/cli/lifecycle/daemon-lifecycle.js +7 -6
- package/dist/command/cli/mcp-command.js +13 -4
- package/dist/command/cli/ports/port-holder.d.ts +11 -0
- package/dist/command/cli/ports/port-holder.js +36 -4
- package/dist/command/cli/setup-mcp-cli.d.ts +27 -1
- package/dist/command/cli/setup-mcp-cli.js +98 -23
- package/dist/command/cli/status/status-lines.d.ts +2 -0
- package/dist/command/cli/status/status-lines.js +72 -17
- package/dist/command/cli/status-fields.d.ts +5 -1
- package/dist/command/cli/status-fields.js +24 -6
- package/dist/command/cli/try-command.d.ts +7 -0
- package/dist/command/cli/try-command.js +11 -3
- package/dist/command/cli/two-builds/compare-command.d.ts +48 -0
- package/dist/command/cli/two-builds/compare-command.js +314 -0
- package/dist/command/cli/verify-against.d.ts +61 -0
- package/dist/command/cli/verify-against.js +187 -0
- package/dist/command/cli/verify-no-session.d.ts +2 -0
- package/dist/command/cli/verify-no-session.js +13 -0
- package/dist/command/cli/verify-results.d.ts +35 -2
- package/dist/command/cli/verify-results.js +76 -10
- package/dist/command/cli.js +112 -70
- package/dist/command/daemon/binding/daemon-status-probe.d.ts +3 -1
- package/dist/command/daemon/binding/daemon-status-probe.js +4 -2
- package/dist/command/daemon/daemon-argv.d.ts +9 -0
- package/dist/command/daemon/daemon-argv.js +11 -0
- package/dist/command/daemon/daemon-resolve.d.ts +8 -1
- package/dist/command/daemon/daemon-resolve.js +27 -1
- package/dist/command/daemon/daemon.d.ts +22 -4
- package/dist/command/daemon/daemon.js +52 -10
- package/dist/command/daemon/lifetime/daemon-exit.d.ts +24 -0
- package/dist/command/daemon/lifetime/daemon-exit.js +39 -0
- package/dist/command/daemon/lifetime/death-cause.d.ts +15 -0
- package/dist/command/daemon/lifetime/death-cause.js +149 -0
- package/dist/command/daemon/lifetime/heartbeat.d.ts +7 -15
- package/dist/command/daemon/lifetime/heartbeat.js +11 -15
- package/dist/command/daemon/lifetime/startup-failure.d.ts +29 -0
- package/dist/command/daemon/lifetime/startup-failure.js +62 -0
- package/dist/command/daemon/port-state.d.ts +14 -0
- package/dist/command/daemon/port-state.js +31 -0
- package/dist/command/setup/agent-configs.d.ts +2 -0
- package/dist/command/setup/agent-configs.js +42 -15
- package/dist/command/setup/agent-next-steps.d.ts +77 -0
- package/dist/command/setup/agent-next-steps.js +284 -0
- package/dist/command/setup/agent-writer.js +11 -6
- package/dist/command/setup/bringup/dev-server-files.d.ts +9 -0
- package/dist/command/setup/bringup/dev-server-files.js +17 -0
- package/dist/command/setup/bringup/static-page-server.d.ts +14 -2
- package/dist/command/setup/bringup/static-page-server.js +43 -9
- package/dist/command/setup/init/init-host.js +2 -0
- package/dist/command/setup/init/init-runtime.d.ts +6 -1
- package/dist/command/setup/init/init-runtime.js +63 -21
- package/dist/command/setup/mcp-launcher.d.ts +3 -0
- package/dist/command/setup/mcp-launcher.js +11 -0
- package/dist/command/setup/node-effects.d.ts +3 -2
- package/dist/command/setup/node-effects.js +9 -3
- package/dist/command/setup/remaining-steps.d.ts +8 -0
- package/dist/command/setup/remaining-steps.js +10 -0
- package/dist/command/setup/run-setup.d.ts +2 -0
- package/dist/command/setup/run-setup.js +9 -1
- package/dist/command/setup/setup-command.js +36 -15
- package/dist/command/setup/setup-mcp.d.ts +8 -0
- package/dist/command/setup/setup-mcp.js +47 -20
- package/dist/command/setup/start-dev-server.d.ts +8 -0
- package/dist/command/setup/start-dev-server.js +43 -0
- package/dist/command/update/updater.js +6 -0
- package/dist/command/version/identity/server-version.d.ts +2 -0
- package/dist/command/version/identity/server-version.js +2 -0
- package/dist/command/version/version-skew.d.ts +7 -0
- package/dist/command/version/version-skew.js +14 -3
- package/dist/features/compare/action-plan.d.ts +260 -0
- package/dist/features/compare/action-plan.js +543 -0
- package/dist/features/compare/behaviour-compare.d.ts +24 -0
- package/dist/features/compare/behaviour-compare.js +85 -0
- package/dist/features/compare/behaviour-diff.d.ts +97 -0
- package/dist/features/compare/behaviour-diff.js +202 -0
- package/dist/features/compare/behaviour-report.d.ts +40 -0
- package/dist/features/compare/behaviour-report.js +128 -0
- package/dist/features/compare/build-readings.d.ts +106 -0
- package/dist/features/compare/build-readings.js +250 -0
- package/dist/features/compare/compare-diff.d.ts +62 -0
- package/dist/features/compare/compare-diff.js +177 -0
- package/dist/features/compare/compare-report-html.d.ts +6 -0
- package/dist/features/compare/compare-report-html.js +102 -0
- package/dist/features/compare/compare-report.d.ts +15 -0
- package/dist/features/compare/compare-report.js +73 -0
- package/dist/features/compare/compare-run.d.ts +60 -0
- package/dist/features/compare/compare-run.js +123 -0
- package/dist/features/compare/outside/effect-lines.d.ts +26 -0
- package/dist/features/compare/outside/effect-lines.js +103 -0
- package/dist/features/compare/outside/state-sources.d.ts +76 -0
- package/dist/features/compare/outside/state-sources.js +164 -0
- package/dist/features/compare/outside/value-dictionary.d.ts +51 -0
- package/dist/features/compare/outside/value-dictionary.js +227 -0
- package/dist/features/compare/visible-content.d.ts +20 -0
- package/dist/features/compare/visible-content.js +125 -0
- package/dist/features/crawl/crawl-empty.js +2 -1
- package/dist/features/crawl/crawl-exhaustive.d.ts +55 -0
- package/dist/features/crawl/crawl-exhaustive.js +138 -0
- package/dist/features/crawl/crawl-tools.d.ts +9 -2
- package/dist/features/crawl/crawl-tools.js +28 -12
- package/dist/features/crawl/crawl.d.ts +8 -9
- package/dist/features/crawl/crawl.js +61 -65
- package/dist/features/exhaust/app-coverage.d.ts +5 -1
- package/dist/features/exhaust/app-coverage.js +3 -1
- package/dist/features/exhaust/code-coverage.js +8 -4
- package/dist/features/exhaust/edge-cases.d.ts +133 -0
- package/dist/features/exhaust/edge-cases.js +310 -0
- package/dist/features/exhaust/edges/edge-drive.d.ts +42 -0
- package/dist/features/exhaust/edges/edge-drive.js +364 -0
- package/dist/features/exhaust/edges/edge-run.d.ts +59 -0
- package/dist/features/exhaust/edges/edge-run.js +169 -0
- package/dist/features/exhaust/explorer.d.ts +87 -14
- package/dist/features/exhaust/explorer.js +159 -25
- package/dist/features/exhaust/failure-branches.d.ts +5 -0
- package/dist/features/exhaust/failure-branches.js +29 -11
- package/dist/features/exhaust/invariants.d.ts +112 -0
- package/dist/features/exhaust/invariants.js +188 -0
- package/dist/features/exhaust/ledger.d.ts +68 -0
- package/dist/features/exhaust/ledger.js +121 -13
- package/dist/features/exhaust/session-fold.d.ts +10 -0
- package/dist/features/exhaust/session-fold.js +46 -3
- package/dist/features/exhaust/session-port.d.ts +3 -1
- package/dist/features/exhaust/session-port.js +97 -28
- package/dist/features/grade/grade-answer.d.ts +99 -0
- package/dist/features/grade/grade-answer.js +112 -0
- package/dist/features/grade/grade-noise.d.ts +27 -0
- package/dist/features/grade/grade-noise.js +55 -0
- package/dist/features/grade/grade-renumber.d.ts +12 -0
- package/dist/features/grade/grade-renumber.js +86 -0
- package/dist/features/grade/grade-state.d.ts +50 -0
- package/dist/features/grade/grade-state.js +93 -0
- package/dist/features/grade/grade-suggest.d.ts +33 -0
- package/dist/features/grade/grade-suggest.js +98 -0
- package/dist/features/license/license.d.ts +11 -71
- package/dist/features/license/license.js +43 -136
- package/dist/features/visual/desktop-capture.d.ts +33 -0
- package/dist/features/visual/desktop-capture.js +94 -0
- package/dist/features/visual/step-shots.js +139 -35
- package/dist/features/visual/visual-tools.d.ts +0 -18
- package/dist/features/visual/visual-tools.js +67 -99
- package/dist/import-graph.js +5 -6
- package/dist/index.d.ts +3 -1
- package/dist/index.js +19 -7
- package/dist/judgement/capsule/causal-summary.js +9 -2
- package/dist/judgement/runs/artifact/replay-mapping.d.ts +13 -1
- package/dist/judgement/runs/artifact/replay-mapping.js +1 -1
- package/dist/judgement/runs/reticle-runner.js +16 -2
- package/dist/judgement/runs/run-ledger.d.ts +7 -5
- package/dist/judgement/runs/run-ledger.js +98 -69
- package/dist/judgement/runs/runner-port.d.ts +2 -0
- package/dist/judgement/runs/runner-port.js +23 -5
- package/dist/judgement/runs/verification-sync.d.ts +6 -3
- package/dist/judgement/runs/verification-sync.js +21 -10
- package/dist/language/flows/affected-tools.d.ts +1 -1
- package/dist/language/flows/affected-tools.js +49 -30
- package/dist/language/flows/change/git-changed.d.ts +2 -1
- package/dist/language/flows/change/git-changed.js +19 -2
- package/dist/language/flows/fields/flow-secret-field.d.ts +1 -13
- package/dist/language/flows/fields/flow-secret-field.js +77 -21
- package/dist/language/flows/flow-anchor.d.ts +60 -2
- package/dist/language/flows/flow-anchor.js +125 -20
- package/dist/language/flows/flow-classify.d.ts +20 -0
- package/dist/language/flows/flow-classify.js +90 -12
- package/dist/language/flows/flow-cross-step.d.ts +7 -1
- package/dist/language/flows/flow-cross-step.js +25 -1
- package/dist/language/flows/flow-journey.d.ts +38 -4
- package/dist/language/flows/flow-journey.js +138 -8
- package/dist/language/flows/flow-replay-run.d.ts +0 -16
- package/dist/language/flows/flow-replay-run.js +76 -14
- package/dist/language/flows/flow-replay-types.d.ts +4 -2
- package/dist/language/flows/flow-replay.d.ts +19 -1
- package/dist/language/flows/flow-replay.js +169 -52
- package/dist/language/flows/flow-replayable.js +7 -1
- package/dist/language/flows/flow-start-path.d.ts +34 -5
- package/dist/language/flows/flow-start-path.js +202 -15
- package/dist/language/flows/flow-step-runners.d.ts +14 -13
- package/dist/language/flows/flow-step-runners.js +184 -109
- package/dist/language/flows/flow-store-for-session.d.ts +26 -25
- package/dist/language/flows/flow-store-for-session.js +51 -5
- package/dist/language/flows/flow-tools.js +46 -33
- package/dist/language/flows/flows.js +176 -76
- package/dist/language/flows/recording/tape/recordings.d.ts +21 -16
- package/dist/language/flows/recording/tape/recordings.js +112 -49
- package/dist/language/flows/replay.d.ts +36 -12
- package/dist/language/flows/replay.js +193 -50
- package/dist/language/flows/steps/page-steps.d.ts +68 -0
- package/dist/language/flows/steps/page-steps.js +198 -0
- package/dist/language/flows/suite/sequential-run.d.ts +68 -0
- package/dist/language/flows/suite/sequential-run.js +96 -0
- package/dist/language/flows/verify-change-tools.js +26 -15
- package/dist/launch-chromium.d.ts +1 -0
- package/dist/launch-chromium.js +49 -12
- package/dist/memory/cloud/background-sync.d.ts +13 -0
- package/dist/memory/cloud/background-sync.js +24 -3
- package/dist/memory/cloud/sync-daemon.js +26 -27
- package/dist/memory/cloud/sync-screenshots.js +6 -1
- package/dist/memory/journal/attach-journal.js +2 -1
- package/dist/memory/journal/drive-flow.d.ts +7 -0
- package/dist/memory/journal/drive-flow.js +44 -13
- package/dist/memory/journal/journal-recorder.d.ts +4 -2
- package/dist/memory/journal/session-journal.d.ts +7 -0
- package/dist/memory/journal/session-journal.js +58 -10
- package/dist/memory/project/root-claims.d.ts +9 -0
- package/dist/memory/project/root-claims.js +9 -4
- package/dist/portal/bridge/bridge.d.ts +13 -4
- package/dist/portal/bridge/bridge.js +10 -9
- package/dist/portal/input/download-capture.d.ts +7 -0
- package/dist/portal/input/download-capture.js +92 -0
- package/dist/portal/input/network-detail.d.ts +6 -0
- package/dist/portal/input/network-detail.js +12 -1
- package/dist/portal/input/network-mock-tools.js +49 -13
- package/dist/portal/input/network-mock.d.ts +8 -0
- package/dist/portal/input/network-mock.js +30 -10
- package/dist/portal/input/page-capture.d.ts +24 -0
- package/dist/portal/input/page-capture.js +33 -0
- package/dist/portal/input/real-input.d.ts +35 -18
- package/dist/portal/input/real-input.js +99 -33
- package/dist/portal/input/viewport-tools.d.ts +8 -0
- package/dist/portal/input/viewport-tools.js +81 -21
- package/dist/portal/pool/browser-pool.d.ts +16 -30
- package/dist/portal/pool/browser-pool.js +64 -52
- package/dist/portal/pool/context-permissions.d.ts +34 -17
- package/dist/portal/pool/context-permissions.js +94 -1
- package/dist/portal/pool/csp-widen.d.ts +62 -0
- package/dist/portal/pool/csp-widen.js +132 -0
- package/dist/portal/pool/determinism.d.ts +52 -0
- package/dist/portal/pool/determinism.js +259 -0
- package/dist/portal/pool/lease-emulation.d.ts +34 -1
- package/dist/portal/pool/lease-emulation.js +18 -0
- package/dist/portal/pool/lease-marker-stamp.d.ts +6 -0
- package/dist/portal/pool/lease-marker-stamp.js +15 -1
- package/dist/portal/pool/lease-page-error.d.ts +56 -0
- package/dist/portal/pool/lease-page-error.js +160 -0
- package/dist/portal/pool/page-error-journal.d.ts +63 -0
- package/dist/portal/pool/page-error-journal.js +208 -0
- package/dist/portal/pool/playwright-launcher.js +71 -15
- package/dist/portal/pool/pool-contract.d.ts +49 -1
- package/dist/portal/pool/pool-lease.d.ts +70 -2
- package/dist/portal/pool/pool-lease.js +23 -0
- package/dist/portal/pool/zero-install.d.ts +8 -0
- package/dist/portal/pool/zero-install.js +91 -1
- package/dist/portal/session/dev-server/dev-command.d.ts +11 -2
- package/dist/portal/session/dev-server/dev-command.js +110 -16
- package/dist/portal/session/dev-server/dev-server-probe.d.ts +7 -0
- package/dist/portal/session/dev-server/dev-server-probe.js +9 -0
- package/dist/portal/session/dev-server/project-ports.d.ts +21 -0
- package/dist/portal/session/dev-server/project-ports.js +62 -0
- package/dist/portal/session/facts/departed-network.d.ts +66 -0
- package/dist/portal/session/facts/departed-network.js +142 -0
- package/dist/portal/session/no-session-diagnosis.d.ts +9 -0
- package/dist/portal/session/no-session-diagnosis.js +76 -27
- package/dist/portal/session/no-session-next-action.d.ts +14 -0
- package/dist/portal/session/no-session-next-action.js +56 -7
- package/dist/portal/session/no-session-watch.d.ts +6 -0
- package/dist/portal/session/no-session-watch.js +41 -4
- package/dist/portal/session/page-commands/undeclared-command.d.ts +9 -3
- package/dist/portal/session/page-commands/undeclared-command.js +16 -7
- package/dist/portal/session/recorded-gaps.d.ts +1 -1
- package/dist/portal/session/recorded-gaps.js +5 -2
- package/dist/portal/session/serving-directory.d.ts +10 -0
- package/dist/portal/session/serving-directory.js +39 -8
- package/dist/portal/session/session-manager.d.ts +10 -0
- package/dist/portal/session/session-manager.js +211 -81
- package/dist/portal/session/session.js +4 -3
- package/dist/portal/session/zero-install-first-call.d.ts +20 -1
- package/dist/portal/session/zero-install-first-call.js +34 -2
- package/dist/start-wiring.d.ts +30 -2
- package/dist/start-wiring.js +74 -9
- package/dist/surface/mcp/mcp-proxy.js +10 -2
- package/dist/surface/mcp/mcp.js +8 -5
- package/dist/surface/mcp/peer/agents-connected.d.ts +6 -0
- package/dist/surface/mcp/peer/agents-connected.js +58 -0
- package/dist/surface/mcp/proxy/proxy-daemon-probe.js +17 -5
- package/dist/surface/mcp/shared-params.d.ts +2 -0
- package/dist/surface/mcp/shared-params.js +31 -0
- package/dist/surface/tools/act/act-observation.d.ts +40 -2
- package/dist/surface/tools/act/act-observation.js +118 -12
- package/dist/surface/tools/act/act-preflight.js +38 -18
- package/dist/surface/tools/act/act-sequence-retry.d.ts +23 -2
- package/dist/surface/tools/act/act-sequence-retry.js +61 -5
- package/dist/surface/tools/act/act-target.js +3 -1
- package/dist/surface/tools/act/after-match.d.ts +10 -0
- package/dist/surface/tools/act/after-match.js +40 -0
- package/dist/surface/tools/act/already-true.js +1 -1
- package/dist/surface/tools/act/navigation/reload-result.d.ts +12 -1
- package/dist/surface/tools/act/navigation/reload-result.js +25 -2
- package/dist/surface/tools/act/resolve-target.d.ts +17 -1
- package/dist/surface/tools/act/resolve-target.js +59 -9
- package/dist/surface/tools/act/sequence-grade.d.ts +15 -1
- package/dist/surface/tools/act/sequence-grade.js +45 -27
- package/dist/surface/tools/act/settle-in-flight.js +27 -15
- package/dist/surface/tools/act-command.d.ts +23 -0
- package/dist/surface/tools/act-command.js +50 -0
- package/dist/surface/tools/act-sequence-tool.js +81 -50
- package/dist/surface/tools/act-tools.d.ts +1 -13
- package/dist/surface/tools/act-tools.js +83 -95
- package/dist/surface/tools/agent/build-staleness.d.ts +1 -1
- package/dist/surface/tools/agent/build-staleness.js +1 -1
- package/dist/surface/tools/assert/assert-verdict.js +18 -12
- package/dist/surface/tools/browser-tools.js +87 -13
- package/dist/surface/tools/compare-tools.d.ts +11 -0
- package/dist/surface/tools/compare-tools.js +94 -0
- package/dist/surface/tools/coverage-tools.js +1 -1
- package/dist/surface/tools/dynamic-tools.js +11 -3
- package/dist/surface/tools/empty-session-list.d.ts +2 -0
- package/dist/surface/tools/empty-session-list.js +4 -2
- package/dist/surface/tools/error-recovery.d.ts +12 -1
- package/dist/surface/tools/error-recovery.js +131 -40
- package/dist/surface/tools/explore-tools.js +1 -1
- package/dist/surface/tools/invoke-tool.js +29 -21
- package/dist/surface/tools/lease-coverage-tools.d.ts +49 -0
- package/dist/surface/tools/lease-coverage-tools.js +128 -0
- package/dist/surface/tools/lease-hint.d.ts +42 -1
- package/dist/surface/tools/lease-hint.js +52 -3
- package/dist/surface/tools/lease-readiness.d.ts +47 -0
- package/dist/surface/tools/lease-readiness.js +126 -0
- package/dist/surface/tools/lease-seed.d.ts +16 -1
- package/dist/surface/tools/lease-seed.js +37 -4
- package/dist/surface/tools/lease-tools.d.ts +3 -41
- package/dist/surface/tools/lease-tools.js +104 -124
- package/dist/surface/tools/lease-url-identity.d.ts +46 -0
- package/dist/surface/tools/lease-url-identity.js +97 -0
- package/dist/surface/tools/merge-tools.js +99 -2
- package/dist/surface/tools/merged-name-redirect.js +5 -1
- package/dist/surface/tools/observe-tools.js +15 -9
- package/dist/surface/tools/read/console-pre-attach.d.ts +19 -0
- package/dist/surface/tools/read/console-pre-attach.js +23 -0
- package/dist/surface/tools/read-tools.js +33 -30
- package/dist/surface/tools/real-input-attempt.d.ts +0 -8
- package/dist/surface/tools/real-input-attempt.js +143 -28
- package/dist/surface/tools/repeat-hint.d.ts +40 -0
- package/dist/surface/tools/repeat-hint.js +171 -0
- package/dist/surface/tools/run-report.d.ts +2 -2
- package/dist/surface/tools/run-report.js +27 -15
- package/dist/surface/tools/session-ports.d.ts +14 -0
- package/dist/surface/tools/session-ports.js +53 -0
- package/dist/surface/tools/tool-kit.d.ts +18 -0
- package/dist/surface/tools/tool-kit.js +9 -3
- package/dist/surface/tools/tool-surface.js +0 -1
- package/dist/surface/tools/tools.js +54 -18
- package/dist/surface/tools/type-spelling.d.ts +13 -0
- package/dist/surface/tools/type-spelling.js +36 -0
- package/dist/telemetry/agent-client.d.ts +6 -0
- package/dist/telemetry/agent-client.js +10 -0
- package/dist/telemetry/argument-shape.js +17 -7
- package/dist/telemetry/cli-telemetry.d.ts +10 -1
- package/dist/telemetry/cli-telemetry.js +15 -0
- package/dist/telemetry/init-telemetry.d.ts +2 -1
- package/dist/telemetry/init-telemetry.js +47 -2
- package/dist/telemetry/install-trace.js +23 -4
- package/dist/telemetry/onboarding-funnel.d.ts +19 -2
- package/dist/telemetry/onboarding-funnel.js +25 -3
- package/dist/telemetry/proxy-telemetry.d.ts +2 -1
- package/dist/telemetry/proxy-telemetry.js +2 -2
- package/dist/telemetry/session-metrics.d.ts +1 -1
- package/dist/telemetry/session-metrics.js +67 -27
- package/dist/telemetry/telemetry.d.ts +3 -1
- package/dist/telemetry/telemetry.js +60 -28
- package/dist/telemetry/tool-refused.d.ts +6 -3
- package/dist/telemetry/tool-refused.js +15 -3
- package/docs/actions.mdx +3 -3
- package/docs/agent-cheatsheet.md +1 -1
- package/docs/architecture.md +3 -6
- package/docs/capabilities.mdx +61 -1
- package/docs/cli/affected.mdx +9 -7
- package/docs/cli/cloud.mdx +3 -3
- package/docs/cli/compare.mdx +94 -0
- package/docs/cli/doctor.mdx +41 -2
- package/docs/cli/grade.mdx +97 -0
- package/docs/cli/help.mdx +4 -2
- package/docs/cli/license.mdx +13 -12
- package/docs/cli/restart.mdx +7 -5
- package/docs/cli/rollback.mdx +5 -5
- package/docs/cli/setup.mdx +13 -2
- package/docs/cli/status.mdx +4 -0
- package/docs/cli/stop.mdx +3 -3
- package/docs/cli/update.mdx +2 -2
- package/docs/cli/verify.mdx +23 -1
- package/docs/cli.mdx +34 -24
- package/docs/deploy-checks.md +25 -0
- package/docs/desktop.mdx +1 -1
- package/docs/enterprise.md +17 -22
- package/docs/environment.mdx +1 -0
- package/docs/first-drive.md +1 -1
- package/docs/flows.md +11 -1
- package/docs/frameworks.mdx +9 -9
- package/docs/getting-started.md +1 -1
- package/docs/install-manual.mdx +16 -1
- package/docs/license-activation.mdx +3 -3
- package/docs/packages/engine.mdx +1 -1
- package/docs/packages/server.mdx +1 -1
- package/docs/packages/tauri.mdx +1 -1
- package/docs/packages/test.mdx +1 -1
- package/docs/packages.mdx +1 -1
- package/docs/platform-integration.md +1 -1
- package/docs/predicates.mdx +1 -1
- package/docs/quickstart.mdx +68 -49
- package/docs/skill-setup.md +1 -1
- package/docs/skill.md +14 -13
- package/docs/telemetry.md +6 -4
- package/docs/tools/navigate.mdx +1 -1
- package/docs/tools/verify.mdx +4 -1
- package/docs/troubleshooting.mdx +1 -1
- package/docs/usage.md +17 -14
- package/package.json +18 -14
- package/LICENSE-ENTERPRISE +0 -37
- package/dist/features/ee/audit-log.d.ts +0 -14
- package/dist/features/ee/audit-log.js +0 -11
- package/dist/features/exhaust/exhaust-run.d.ts +0 -33
- package/dist/features/exhaust/exhaust-run.js +0 -82
package/docs/capabilities.mdx
CHANGED
|
@@ -105,6 +105,62 @@ The reliable pattern is:
|
|
|
105
105
|
3. Advance by the required interval.
|
|
106
106
|
4. Assert the consequence.
|
|
107
107
|
|
|
108
|
+
### Deterministic lease: the same pixels on every run
|
|
109
|
+
|
|
110
|
+
A canvas game or an animation draws something different on each run, because time and randomness differ. Acquire a lease with `deterministic` to make two runs the same:
|
|
111
|
+
|
|
112
|
+
```json
|
|
113
|
+
{ "tool": "reticle_lease", "args": { "action": "acquire", "url": "http://localhost:5173", "deterministic": { "seed": 7, "platform": "Linux x86_64" } } }
|
|
114
|
+
{ "tool": "reticle_clock", "args": { "stepFrames": 30 } }
|
|
115
|
+
```
|
|
116
|
+
|
|
117
|
+
```json
|
|
118
|
+
{ "frozen": true, "frame": 30, "nowMs": 500 }
|
|
119
|
+
```
|
|
120
|
+
|
|
121
|
+
Before any page script runs, the lease installs these in the tab:
|
|
122
|
+
|
|
123
|
+
- `Math.random`, `crypto.getRandomValues` and `crypto.randomUUID` take values from a generator with the given `seed` (default 1).
|
|
124
|
+
- `Date`, `performance.now`, `setTimeout`, `setInterval` and `requestAnimationFrame` use a virtual clock. It starts at 2026-01-01T00:00:00Z and moves only on `stepFrames`.
|
|
125
|
+
- `devicePixelRatio` is 1. `platform` sets `navigator.platform`, the platform in `navigator.userAgent` and `navigator.userAgentData.platform`.
|
|
126
|
+
|
|
127
|
+
Each step frame is 16.67 ms. In each frame, the due timers run in time order, then each `requestAnimationFrame` callback runs once. Then capture or read the page.
|
|
128
|
+
|
|
129
|
+
<Warning>
|
|
130
|
+
Time stands still on this tab until you step it. A wait for a timer or an animation does not end
|
|
131
|
+
on its own. These still run on real time: CSS animations and transitions, workers, WebAssembly
|
|
132
|
+
threads, media playback and network responses. Mock the network with `reticle_network_mock` if the
|
|
133
|
+
page draws what it fetches. GPU drawing can differ between machines; compare runs on the same
|
|
134
|
+
machine.
|
|
135
|
+
</Warning>
|
|
136
|
+
### JS coverage of a leased tab: which code ran
|
|
137
|
+
|
|
138
|
+
The JS engine counts each block of code that runs. On a leased tab, Reticle reads those counts from outside the app, with no change to it:
|
|
139
|
+
|
|
140
|
+
```json
|
|
141
|
+
{ "tool": "reticle_lease", "args": { "action": "acquire", "url": "http://localhost:5173", "jsCoverage": true } }
|
|
142
|
+
{ "tool": "reticle_lease", "args": { "action": "coverage", "mode": "take", "urlContains": "/src/" } }
|
|
143
|
+
```
|
|
144
|
+
|
|
145
|
+
```json
|
|
146
|
+
{
|
|
147
|
+
"running": true,
|
|
148
|
+
"scriptCount": 1,
|
|
149
|
+
"rangeCount": 3,
|
|
150
|
+
"scripts": [
|
|
151
|
+
{
|
|
152
|
+
"url": "http://localhost:5173/src/app.js",
|
|
153
|
+
"ranges": [
|
|
154
|
+
{ "startOffset": 0, "endOffset": 412, "count": 1 },
|
|
155
|
+
{ "startOffset": 120, "endOffset": 188, "count": 0 }
|
|
156
|
+
]
|
|
157
|
+
}
|
|
158
|
+
]
|
|
159
|
+
}
|
|
160
|
+
```
|
|
161
|
+
|
|
162
|
+
A take returns what ran since the previous take. A range with `count: 0` is code that did not run. `jsCoverage: true` on acquire starts coverage before the page's first script, so the code that runs while the page loads is counted. `{ "mode": "start" }` starts it later, and misses that code. A take stops at `maxRanges` (default 20000) and names what it dropped in `truncated`; `filteredOut` counts the scripts that `urlContains` left out. Chromium only.
|
|
163
|
+
|
|
108
164
|
### Crawl: click everything, report anomalies
|
|
109
165
|
|
|
110
166
|
```json
|
|
@@ -147,7 +203,9 @@ Controls Reticle judges destructive are blocked unless you pass `confirmDangerou
|
|
|
147
203
|
|
|
148
204
|
`{ "action": "crawl", "exhaustive": true }` goes past one page. It walks every state reachable from where you start, reaching each one by replaying the path that found it from a fresh load, so it never depends on "back" working. It fills text fields before it tries a form's buttons (from `RETICLE_SECRET_<FIELD>` when set, so it gets past a login, and only on the origin the crawl started on), and treats controls that differ only by a number, like table rows, as one. A control with the same name on a different screen is tried again there. Every write it finds is then driven again with the request failing. A write counts as **branched** only when the request was actually sent and broken. With the write failing, the app must not end up where it goes when the write succeeds; if it does, you get `failure-unhandled`. That part needs a browser Reticle drives (`reticle drive`).
|
|
149
205
|
|
|
150
|
-
The run folds into the app-wide coverage ledger, which `reticle_verify { action: "coverage", app: true }` also reports. It has six levels, each with what is missing: routes **reached**, controls **touched**, controls **proved** (an `act_and_wait` came back `yes`), journeys **completed**, writes **branched** (failure path driven), and app functions **executed** (
|
|
206
|
+
The run folds into the app-wide coverage ledger, which `reticle_verify { action: "coverage", app: true }` also reports. It has six levels, each with what is missing: routes **reached**, controls **touched**, controls **proved** (an `act_and_wait` came back `yes`), journeys **completed**, writes **branched** (failure path driven), and app functions **executed** (JS coverage, driven browser only, collected from the first coverage request or exhaustive crawl onward, so an ordinary drive pays nothing for it). `frontier` is the number of states found and not yet explored. Zero means every state the explorer could tell apart was explored, not that every reachable state was: a state is its route plus the names of its controls, so two screens that differ only in field values, in how many of a control they show, or in what the same controls do count as one, and the second is never visited. `reticle gate` blocks when a level falls below the best it has reached, and when a changed file never ran. A changed file whose coverage was taken before the edit is reported as `coverageStale` instead, because its counts describe the old code. When a drop was intended, `reticle gate --accept-coverage` records today's levels as the new best.
|
|
207
|
+
|
|
208
|
+
The same report has a `holes` block. It names what was never reached, by kind: `routes`, `controls`, `edges` (controls whose edge-case inputs and interactions were never driven), `writes` (failure path never driven), `functions` and `components`. A kind that nothing could measure has `measured: false` and a `note` that tells you why. A list past its cap has `overflow`, the count of the items it does not name. The `findings` block lists the behaviour faults in the ledger: `undo-not-restored`, `repeat-changed-state`, `lost-after-reload`, `shown-differs-from-sent`, `intermittent-result` and `failure-unhandled`. Each finding has the steps that show it, and the `file:line` of the element when the app gives source attribution.
|
|
151
209
|
|
|
152
210
|
<Warning>
|
|
153
211
|
Exhaustive really does click everything, repeatedly, and submits forms. `maxSteps` bounds it,
|
|
@@ -425,6 +483,8 @@ Nine hundred and fifty-three bytes for 445 recorded events. `timeline_omitted` h
|
|
|
425
483
|
|
|
426
484
|
Reticle grades the flow as you save it, and tells you when you have just created a test that cannot fail. Take the warning seriously: an assertion-free flow replays green whatever the app does.
|
|
427
485
|
|
|
486
|
+
When the flow checks something, `assertions.checks` counts each kind of check over every step, sub-step and the success state, for example `{ "element": 1, "route": 1, "text": 3 }`. A presence-only flow names those checks in its warning. The grade says how strong the checks are, not that there are none.
|
|
487
|
+
|
|
428
488
|
A replay against a drifted app names what moved and where. This is `reticle_verify { action: "flows" }` reporting the same flow after the app changed underneath it:
|
|
429
489
|
|
|
430
490
|
```json
|
package/docs/cli/affected.mdx
CHANGED
|
@@ -1,15 +1,17 @@
|
|
|
1
1
|
---
|
|
2
|
-
title: reticle
|
|
2
|
+
title: reticle gate --list
|
|
3
3
|
description: List which saved flows must re-verify for a set of changed files.
|
|
4
4
|
icon: code-branch
|
|
5
5
|
---
|
|
6
6
|
|
|
7
|
-
`reticle
|
|
7
|
+
`reticle gate --list` answers one question: given these changed files, which saved flows cover them? The [gate](/cli/gate) checks the same set. `--list` only names it and checks nothing. It costs your agent nothing per turn because it runs in the environment.
|
|
8
8
|
|
|
9
9
|
```bash
|
|
10
|
-
npx @reticlehq/server
|
|
10
|
+
npx @reticlehq/server gate --list [--since <ref>] [file...]
|
|
11
11
|
```
|
|
12
12
|
|
|
13
|
+
`reticle affected` is the old name. It still works for one release and prints one line naming `gate --list`.
|
|
14
|
+
|
|
13
15
|
## Arguments and flags
|
|
14
16
|
|
|
15
17
|
| Argument | Type | Default | What it does |
|
|
@@ -17,7 +19,7 @@ npx @reticlehq/server affected [--since <ref>] [file...]
|
|
|
17
19
|
| `file...` | strings, positional | none | Explicit changed files |
|
|
18
20
|
| `--since <ref>` | string | `HEAD` when no files are given | Also include files git reports as changed since this ref |
|
|
19
21
|
|
|
20
|
-
With
|
|
22
|
+
With no files, `reticle gate --list` compares the working tree with `HEAD`.
|
|
21
23
|
|
|
22
24
|
## What it prints
|
|
23
25
|
|
|
@@ -43,11 +45,11 @@ The real run named 47 flows in each list. The CLI prints this as a single line o
|
|
|
43
45
|
|
|
44
46
|
## Exit codes
|
|
45
47
|
|
|
46
|
-
Always `0`. A load error is logged as `reticle_affected_failed`, not thrown. Use [`reticle gate`](/cli/gate) when you want a non-zero exit.
|
|
48
|
+
Always `0`. A load error is logged as `reticle_affected_failed`, not thrown. Use [`reticle gate`](/cli/gate) without `--list` when you want a non-zero exit.
|
|
47
49
|
|
|
48
50
|
## Worked example
|
|
49
51
|
|
|
50
52
|
```bash
|
|
51
|
-
npx @reticlehq/server
|
|
52
|
-
npx @reticlehq/server
|
|
53
|
+
npx @reticlehq/server gate --list --since origin/main
|
|
54
|
+
npx @reticlehq/server gate --list src/components/Login.tsx
|
|
53
55
|
```
|
package/docs/cli/cloud.mdx
CHANGED
|
@@ -42,7 +42,7 @@ npx @reticlehq/server connect [--project <name|id>] [--workspace <name|id>] [--u
|
|
|
42
42
|
|
|
43
43
|
Signs in if needed (a browser device flow like `gh auth login`: approve in the browser, the CLI polls until confirmed), then binds this repository to a cloud project and sends local history. It **mints** a project-scoped key, so there is nothing to paste; with `RETICLE_API_KEY` already set, it resolves that key's project instead. `--project` accepts a slug id or a display name, and creates the project when no project has that name. Omitted, the project is named after the `projectId` in `.reticle.json`, else after this folder. `--workspace` picks the workspace to link in when you belong to more than one. `--no-install` is passed to the `init` it runs for an unwired app. Writes `cloud.json` and the key.
|
|
44
44
|
|
|
45
|
-
`reticle login`, `reticle link` and `reticle project`
|
|
45
|
+
`reticle login`, `reticle link` and `reticle project` were removed. Each prints that it was removed, names `connect`, and exits `1`. Sign-in is with Google or GitHub, in the browser. Email sign-in is gone. Without a browser (CI, an agent, a server), set `RETICLE_API_KEY` to a key from Settings > API keys.
|
|
46
46
|
|
|
47
47
|
### `reticle logout`
|
|
48
48
|
|
|
@@ -74,7 +74,7 @@ Sends local run artifacts from `.reticle` to the linked project, honoring the sy
|
|
|
74
74
|
|
|
75
75
|
Runs go up in batches, so a large backlog is never one oversized request.
|
|
76
76
|
|
|
77
|
-
`reticle push`
|
|
77
|
+
`reticle push` was removed: use `reticle sync`. Add `--watch` to keep syncing: it runs one cycle, waits, and runs the next, until you stop it with `Ctrl+C`. The wait is 60 seconds by default; set `RETICLE_SYNC_INTERVAL_MS` to change it. Add `--move-history` to also send the runs, flows and records made under this folder's previous link, after it was linked to another workspace.
|
|
78
78
|
|
|
79
79
|
```bash
|
|
80
80
|
npx @reticlehq/server sync --watch
|
|
@@ -115,7 +115,7 @@ The triage queue from the dashboard. `--fix <fingerprint>` prints that one issue
|
|
|
115
115
|
|
|
116
116
|
What the linked project has learned, scoped to the project this folder is linked to. `--subject <name>` narrows it to one area. If the response cannot be shown to be about this project, it prints nothing on stdout and exits `1`.
|
|
117
117
|
|
|
118
|
-
`reticle regression`, `reticle share`, `reticle issues` and `reticle memory`
|
|
118
|
+
`reticle regression`, `reticle share`, `reticle issues` and `reticle memory` were removed. Each prints the `runs` form to use and exits `1`.
|
|
119
119
|
|
|
120
120
|
## When the repo is not attached
|
|
121
121
|
|
|
@@ -0,0 +1,94 @@
|
|
|
1
|
+
---
|
|
2
|
+
title: reticle compare
|
|
3
|
+
description: Drive two running builds of one app the same way and list each difference in what users see.
|
|
4
|
+
icon: code-compare
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
`reticle compare` answers one question: does the candidate build show what the reference build shows? Use it to compare main with a pull request preview, or a known-good build with a changed build. The app needs nothing installed: no SDK, no plugin and no `reticle init`. Any URL works.
|
|
8
|
+
|
|
9
|
+
```bash
|
|
10
|
+
npx @reticlehq/server compare <reference-url> <candidate-url> [--base <url>] [--state <file>] [--json] [--report <file>]
|
|
11
|
+
```
|
|
12
|
+
|
|
13
|
+
| Argument | Type | Default | What it does |
|
|
14
|
+
| --- | --- | --- | --- |
|
|
15
|
+
| `<reference-url>` | string | required | The build that is correct, for example main |
|
|
16
|
+
| `<candidate-url>` | string | required | The build to check, for example a pull request preview |
|
|
17
|
+
| `--base <url>` | string | unset | The build before the change. Each difference gets a tag, and the command prints a score |
|
|
18
|
+
| `--state <file>` | string | unset | A JSON file that declares how to read the app's stored data. See [State sources](#state-sources) |
|
|
19
|
+
| `--json` | boolean | off | Print one JSON object instead of text |
|
|
20
|
+
| `--report <file>` | string | unset | Also write the result as one HTML page: the verdict, the counts, and each difference with its steps and the lines on each side. Open it in a browser, share it, or keep it as a CI artifact. It needs no network and runs no script |
|
|
21
|
+
|
|
22
|
+
## What it does
|
|
23
|
+
|
|
24
|
+
The command has one recipe and no other settings.
|
|
25
|
+
|
|
26
|
+
1. **Read the values the app checks for.** The command fetches the reference page and its scripts the way a browser does (at most 40 files). It collects each string that a named value is compared with, for example `values.route === "progress"`. A field whose name matches that name also gets those values, so a branch behind a special value is reached.
|
|
27
|
+
2. **Plan on the reference, breadth first.** The plan has the start page and every single action on every control. It clicks each button, tab, checkbox and option. It fills each text field with two values chosen by the shape of the field's value (a time, a date, a number, text), one edge value of that shape (`23:59`, `2024-02-29`, `-1`, or a long text with markup characters), and the values from step 1. It selects each option of each combobox. After each sequence, the plan goes one level deeper into the controls that appeared. On a page with two or more fields, it fills every field with its own value, then presses each button. A click is also followed by a 4 second wait, but only where the reference showed delayed activity: a request still pending, a page that kept changing while it settled, or a change during the wait. The plan holds at most 220 sequences. A control is found by its test id when it has one, else by its role and name, numbered in page order.
|
|
28
|
+
3. **Drive the plan.** Every sequence starts from a fresh load of the URL. The page is read only when it settles: two reads in a row, 400 ms apart, must match (at most 4 reads). A sequence that starts a longer planned sequence is not driven alone; the longer one is read after each step. The reference is driven two times, the candidate one time, and the base one time. Each run is a new browser tab that the daemon leases.
|
|
29
|
+
4. **Compare what a person sees, and what the app did.** Names, text, values, and the checked, selected, disabled, expanded and pressed states, in page order. Then each network call since the sequence's first action (method, path with the query values removed, status, and the start of the request body) and each console error and warning. Case and spacing of page text are folded, and elapsed times under one second are rounded to whole seconds. A line that differs between the two reference runs (a clock, a random id) is noise and is ignored. A step that the candidate cannot do and the reference could is a difference. When a network or console read fails, the reading says `effects failed`, so an empty list always means that nothing happened.
|
|
30
|
+
|
|
31
|
+
The command presses every button it finds. On a build served from loopback (`localhost`, `127.0.0.1`) or a `*.localhost` name, that includes the controls the act guard holds back, such as "Place order" or "Delete": those builds are disposable copies, and their submits are the actions most worth comparing. On any other host the guard stays on and those controls are not pressed. Point it at builds whose data you can change, not at a production database.
|
|
32
|
+
|
|
33
|
+
## State sources
|
|
34
|
+
|
|
35
|
+
A page read sees only the pages that a sequence opens. If the candidate also changes a record that no page in the plan shows (for example, the price of another product), the page reads cannot see it. Declare how to read the app's stored data, and compare reads it too:
|
|
36
|
+
|
|
37
|
+
```json
|
|
38
|
+
{
|
|
39
|
+
"sources": [
|
|
40
|
+
{
|
|
41
|
+
"kind": "command",
|
|
42
|
+
"label": "prices",
|
|
43
|
+
"container": "shop-db",
|
|
44
|
+
"command": "mysql -N shop -e 'select entity_id, value from product_price'"
|
|
45
|
+
},
|
|
46
|
+
{
|
|
47
|
+
"kind": "http",
|
|
48
|
+
"label": "orders",
|
|
49
|
+
"url": "http://localhost:3000/api/orders",
|
|
50
|
+
"path": "data.items",
|
|
51
|
+
"ignore": ["updatedAt"]
|
|
52
|
+
},
|
|
53
|
+
{ "kind": "file", "label": "settings", "path": "./data/settings.json" }
|
|
54
|
+
]
|
|
55
|
+
}
|
|
56
|
+
```
|
|
57
|
+
|
|
58
|
+
| Kind | Fields | What it reads |
|
|
59
|
+
| --- | --- | --- |
|
|
60
|
+
| `command` | `command`, optional `container` | Each output line of a shell command. With `container`, the command runs through `docker exec <container> sh -c` |
|
|
61
|
+
| `http` | `url`, optional `path` | Each record of a JSON endpoint. `path` is a dotted path to the array |
|
|
62
|
+
| `file` | `path`, optional `at`, optional `container` | Each JSON record of a file (`at` is a dotted path to the array), or each line when the file is not JSON. With `container`, the file is read in that container |
|
|
63
|
+
|
|
64
|
+
Each source has a `label`. `ignore` is optional: for JSON records it holds field names to remove, and for text lines it holds regular expressions to remove (a time, or an id that changes on each run). A text line that a pattern removes all of is removed.
|
|
65
|
+
|
|
66
|
+
After each sequence, on every build, compare reads each source and adds its rows to that sequence's reading as `state <label> <row>` lines, sorted. JSON records are written with their keys sorted. The same diff and the same noise rule apply: a row that differs between the two reference runs is ignored. Start each row with the record id, so that a changed row names its record. A source keeps at most 1000 rows. When it has more, a `state rows cut: <label>: kept 1000 of <n>, rest <digest>` line says so. The digest covers the cut rows, so a change to a cut row changes this line, but the line does not name the record. If a cut row differs between the two reference runs, the digest is noise and a change to a cut row is not seen. Remove times with `ignore`, or query fewer rows. A read that fails gives a `state read failed: <label>: <reason>` line, never an empty list.
|
|
67
|
+
|
|
68
|
+
The builds are driven one after the other, and compare does not reset their data. When two builds use one database, the second build starts from the data the first one changed. Give each build its own data, or reset it before each run.
|
|
69
|
+
|
|
70
|
+
## What it prints
|
|
71
|
+
|
|
72
|
+
The first line is the verdict: `SAME`, `DIFFERENT` or `INVALID`. Then the counts, the time for each build in seconds, and the first 5 differences. Each difference shows the steps that reproduce it, then `-` for the lines only the reference shows and `+` for the lines only the candidate shows. `--json` gives every difference.
|
|
73
|
+
|
|
74
|
+
With `--base`, each difference gets a tag:
|
|
75
|
+
|
|
76
|
+
| Tag | Meaning |
|
|
77
|
+
| --------------- | --------------------------------------------------------------------------- |
|
|
78
|
+
| `regression` | The base and the reference show the same page, and the candidate changed it |
|
|
79
|
+
| `target-missed` | The reference changed the page, and the candidate still shows the base page |
|
|
80
|
+
| `changed` | The candidate differs from both |
|
|
81
|
+
|
|
82
|
+
The score is `targets matched / targets x (1 - kept sequences changed / kept)`. A target is a sequence where the reference changed the base page. A kept sequence is one where it did not.
|
|
83
|
+
|
|
84
|
+
## Exit codes
|
|
85
|
+
|
|
86
|
+
| Code | Meaning |
|
|
87
|
+
| --- | --- |
|
|
88
|
+
| `0` | Same: every compared sequence shows the same page |
|
|
89
|
+
| `1` | Different |
|
|
90
|
+
| `2` | Invalid: the browser session was lost, nothing could be compared, or the daemon or a build could not be reached. Run it again |
|
|
91
|
+
|
|
92
|
+
The command uses the daemon on `--port` (or `RETICLE_PORT`), and starts one when there is none.
|
|
93
|
+
|
|
94
|
+
An agent whose Reticle tools are loaded runs the same compare with `reticle_verify { action: "compare", reference, candidate, base? }`. It answers the same JSON as `--json`; see [reticle_verify](/tools/verify).
|
package/docs/cli/doctor.mdx
CHANGED
|
@@ -7,13 +7,14 @@ icon: stethoscope
|
|
|
7
7
|
`reticle doctor` collapses the setup failure modes into one command. It is the first thing to run when something is wrong.
|
|
8
8
|
|
|
9
9
|
```bash
|
|
10
|
-
npx @reticlehq/server doctor [--port N]
|
|
10
|
+
npx @reticlehq/server doctor [--fix] [--port N]
|
|
11
11
|
```
|
|
12
12
|
|
|
13
13
|
## Flags
|
|
14
14
|
|
|
15
15
|
| Flag | Type | Default | What it does |
|
|
16
16
|
| --- | --- | --- | --- |
|
|
17
|
+
| `--fix` | boolean | off | Repair what Reticle can repair safely, then run the checks again. See [Repair with --fix](#repair-with---fix) |
|
|
17
18
|
| `--port N` | number | `RETICLE_PORT`, else the port in `.reticle.json`, else the daemon already serving this project, else `4400` | Which bridge port to diagnose |
|
|
18
19
|
|
|
19
20
|
## What it prints
|
|
@@ -50,10 +51,12 @@ When nothing has connected, the `sessions` line fails and the daemon's own diagn
|
|
|
50
51
|
| Line | What it checks |
|
|
51
52
|
| --- | --- |
|
|
52
53
|
| `node` | The Node version running the CLI |
|
|
54
|
+
| `mcp` | Which coding agents found on this machine have Reticle's MCP server registered. Fails when an agent is found without it, and names the agent and `reticle setup mcp` |
|
|
53
55
|
| `chromium` | Whether the exact Chromium revision the bundled Playwright wants is on disk. The most common silent failure |
|
|
54
56
|
| `daemon` | Whether the port holds a Reticle daemon, a foreign process (named where possible), or nothing. Adds a `version` line when the daemon's version or contract fingerprint disagrees with the CLI's |
|
|
55
57
|
| `sessions` | Whether any page has actually connected. Zero is a FAILING check rather than a neutral note, because it is the state the setup most often stalls in: wired correctly, daemon up, nothing dialled in. When it is zero the daemon's own no-session diagnosis prints below the checklist |
|
|
56
58
|
| `agent link` | Whether an MCP client has listed Reticle's tools on this port **and actually called one**. Every other row here checks a component; this one checks the hop between your agent and the daemon. It is possible for the SDK to be injected, a session to be live, and your client to show every tool enabled, while no request has ever crossed from the agent. That state passes every other check and is the one people lose hours to |
|
|
59
|
+
| `launcher` | Only when an agent config starts Reticle from an installed copy (`node <path> mcp`) and that file does not exist, for example after `npm uninstall -g`. Names the agent, the path, and the command that writes a working entry |
|
|
57
60
|
| `loopback` | Which of `localhost`'s two answers reaches the bridge. Printed **only when they disagree**. The daemon binds `127.0.0.1`, and a best-effort alias forwards `[::1]` to it so the name works everywhere. When that alias cannot open (IPv6 disabled, or something already holding `[::1]` on the port) the daemon serves IPv4 perfectly and a page told to dial `localhost` still cannot reach it, because Windows Chrome tries the IPv6 answer first. Every other row here goes green in that state |
|
|
58
61
|
| `bridge port` | The port your app must dial, spelled out because mixing it up with the dev server port is the most common setup failure |
|
|
59
62
|
| `port check` | Only when your project's configured port disagrees with the one the daemon is on. Prints the mismatch rather than leaving you to spot it across two lines |
|
|
@@ -113,9 +116,45 @@ The wanted revision and the root are both read back off the path Playwright itse
|
|
|
113
116
|
before. That loop is why the line names the version to pin to.
|
|
114
117
|
</Warning>
|
|
115
118
|
|
|
119
|
+
## Repair with --fix
|
|
120
|
+
|
|
121
|
+
When a row has a safe repair, a plain `doctor` run ends with one more line:
|
|
122
|
+
|
|
123
|
+
```
|
|
124
|
+
Run `reticle doctor --fix` to repair 2 of these.
|
|
125
|
+
```
|
|
126
|
+
|
|
127
|
+
`reticle doctor --fix` prints the checks, applies the safe repairs in a fixed order, runs the checks again, and prints one line for each repair and one for each row that still fails. A repair changes only Reticle's own state:
|
|
128
|
+
|
|
129
|
+
| Order | Row | Repair | Done only when |
|
|
130
|
+
| --- | --- | --- | --- |
|
|
131
|
+
| 1 | `daemon` | Delete the pid file of a daemon that is not running | The process that the file names does not exist |
|
|
132
|
+
| 2 | `daemon` | Stop a Reticle daemon that holds the port and does not answer, as `reticle serve --restart` does | The holder's command line is a Reticle daemon, and it is still silent after a grace period. A different program and the agent's own `reticle mcp` proxy are never stopped |
|
|
133
|
+
| 3 | `chromium` | Install the pinned Chromium of the bundled Playwright (a download) | No Chrome or Edge can stand in, and `RETICLE_CHROMIUM_PATH` is not set |
|
|
134
|
+
| 4 | `launcher` | Run `reticle setup mcp`, which replaces Reticle's own entry | An agent config starts Reticle from an installed copy that does not exist. `setup mcp` keeps an existing Claude Code entry, so for Claude Code the step stays `claude mcp remove reticle -s user`, then `setup mcp` |
|
|
135
|
+
| 5 | `mcp` | Run `reticle setup mcp` | An agent on this machine does not have Reticle registered |
|
|
136
|
+
|
|
137
|
+
Each repair checks again before it acts, so a second `--fix` finds nothing to do and changes nothing.
|
|
138
|
+
|
|
139
|
+
`--fix` never repairs a row that needs a change to your app, a process that Reticle cannot prove is its own daemon, or an action only you can do. For those rows it prints the step that the row names: for example `reticle init` for `project`, starting your agent for a stopped `daemon`, `reticle hook install` for `prompts`, a CSP or desktop change, or a version skew (restart the daemon when no other agent uses it).
|
|
140
|
+
|
|
141
|
+
```
|
|
142
|
+
reticle doctor --fix
|
|
143
|
+
daemon pid file of a stopped daemon: fixed
|
|
144
|
+
daemon a Reticle daemon that does not answer: nothing to do
|
|
145
|
+
chromium Playwright's own Chromium: nothing to do
|
|
146
|
+
launcher a registered launcher that does not exist: nothing to do
|
|
147
|
+
mcp agent registrations: fixed
|
|
148
|
+
still needs: sync ✗ off: this project is not linked: run `reticle connect`; no push yet
|
|
149
|
+
```
|
|
150
|
+
|
|
151
|
+
A registration takes effect when the agent reads its config again, so restart your agent after `mcp` is fixed.
|
|
152
|
+
|
|
116
153
|
## Exit codes
|
|
117
154
|
|
|
118
|
-
|
|
155
|
+
A plain `doctor` always exits `0`. It reports; it does not gate.
|
|
156
|
+
|
|
157
|
+
`doctor --fix` exits `0` only when no row fails after the repairs, and `1` otherwise.
|
|
119
158
|
|
|
120
159
|
## Worked example
|
|
121
160
|
|
|
@@ -0,0 +1,97 @@
|
|
|
1
|
+
---
|
|
2
|
+
title: reticle grade
|
|
3
|
+
description: Grade a finished run of an app from snapshots of its stored data, and check its final answer.
|
|
4
|
+
icon: clipboard-check
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
`reticle grade` answers one question: did a run leave the app the way the correct steps leave it, and give the correct answer? A run is any sequence of steps on an app you can reset: an agent, a script or a person. The command needs no daemon, no browser and nothing installed in the app. It reads the app's stored data through the [state sources](/cli/compare#state-sources) that `reticle compare --state` uses.
|
|
8
|
+
|
|
9
|
+
```bash
|
|
10
|
+
npx @reticlehq/server grade snapshot --state <file> --out <file> [--url <url>]
|
|
11
|
+
npx @reticlehq/server grade judge --reference <file> --again <file> --candidate <file> [--expect <file>] [--answer <text>] [--json]
|
|
12
|
+
npx @reticlehq/server grade tables --list <command> --rows <template> [--container <name>] [--skip <prefix,...>] --out <file>
|
|
13
|
+
npx @reticlehq/server grade suggest --state <file> --reference <file> --again <file> --out <file>
|
|
14
|
+
```
|
|
15
|
+
|
|
16
|
+
## How to grade a run
|
|
17
|
+
|
|
18
|
+
1. Reset the app. Do the correct steps. Run `grade snapshot --out reference.json`.
|
|
19
|
+
2. Reset the app. Do the correct steps again. Run `grade snapshot --out again.json`.
|
|
20
|
+
3. Reset the app. Do the run to grade. Run `grade snapshot --out candidate.json`.
|
|
21
|
+
4. Run `grade judge --reference reference.json --again again.json --candidate candidate.json`.
|
|
22
|
+
|
|
23
|
+
Steps 1 and 2 are done one time for each task. Keep the two files, and grade every run of the task against them.
|
|
24
|
+
|
|
25
|
+
`judge` compares the lines of the three snapshots. A line that differs between the two correct runs (a clock, a random id) is noise and is ignored. Any other line that differs between the reference and the candidate is a difference, and the grade fails. So the grade fails when the run changed the wrong record, changed a record the task did not name, or did not change the record at all. A source that could not be read makes the grade unverified, never a pass.
|
|
26
|
+
|
|
27
|
+
A row that the two correct runs wrote with different values in some cells (a time of the run, written into `updated_at`) has noise in those cells only. A candidate row that differs from the reference row only in those cells is not a difference. A change to another cell of that row, or to the same cell of another row, is a difference.
|
|
28
|
+
|
|
29
|
+
Many apps save a record by deleting its child rows and writing them again, with new ids. A run that saves a record two times then has the same data under other ids. `judge` matches these rows: a removed row and an added row of one source are the same record when every cell after the first (the id) is equal, after each id it already matched is replaced by its new id. So a row that links to a written-again row matches too. A match needs an old id that the candidate no longer has, and a new id that the reference did not have, so a changed value in a first column that is not an id is still a difference. `--json` gives the count as `state.renumbered`. This applies to text rows (a `command` source, or a file of plain lines) whose cells are separated by tabs.
|
|
30
|
+
|
|
31
|
+
| Exit code | Verdict | Meaning |
|
|
32
|
+
| --------- | ------------ | ------------------------------------------------------------------ |
|
|
33
|
+
| 0 | `PASS` | The stored data matches, and the answer is correct |
|
|
34
|
+
| 1 | `FAIL` | A line differs, or the answer is wrong |
|
|
35
|
+
| 2 | `UNVERIFIED` | A source or a snapshot could not be read. The grade proves nothing |
|
|
36
|
+
|
|
37
|
+
`--json` prints one JSON object: `verdict`, `state.removed` and `state.added` (every line that differs), `state.ignored`, `answer` and `unread`. The text output shows the first 10 lines on each side and says how many it left out.
|
|
38
|
+
|
|
39
|
+
## Snapshot
|
|
40
|
+
|
|
41
|
+
`grade snapshot --state <file> --out <file>` reads each declared source and writes its rows as `state <label> <row>` lines, sorted. A snapshot keeps every row: unlike `compare`, it has no 1000-row cap, so a changed row always names its record. A read that fails gives a `state read failed: <label>: <reason>` line, and the command exits 2.
|
|
42
|
+
|
|
43
|
+
`--url <url>` adds the page the run ended on, as a `url` line. Use it for a task whose goal is to open a page. The fragment and a final slash are removed, and the query values are sorted.
|
|
44
|
+
|
|
45
|
+
## Check the answer
|
|
46
|
+
|
|
47
|
+
A task that asks a question has a final answer. A fixed answer string goes stale when the data changes. Declare a source whose rows are the correct answer instead, and `judge` reads it when it grades:
|
|
48
|
+
|
|
49
|
+
```json
|
|
50
|
+
{
|
|
51
|
+
"answer": {
|
|
52
|
+
"source": {
|
|
53
|
+
"kind": "command",
|
|
54
|
+
"label": "answer",
|
|
55
|
+
"container": "shop-db",
|
|
56
|
+
"command": "mysql -N shop -e \"select count(*) from sales_order where customer_email = 'jane@example.com'\""
|
|
57
|
+
},
|
|
58
|
+
"match": "number",
|
|
59
|
+
"none": ["N/A"]
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
```
|
|
63
|
+
|
|
64
|
+
Give the file with `--expect`, and the run's answer with `--answer`. Text is folded before it is compared: Unicode normal form, lower case, spacing, quotes and a final full stop.
|
|
65
|
+
|
|
66
|
+
| `match` | The answer passes when |
|
|
67
|
+
| --- | --- |
|
|
68
|
+
| `exact` (default) | It is the one value in the rows. With more than one row, it is checked as `set` |
|
|
69
|
+
| `number` | It is one number and nothing else, equal to the first value within 0.005. `$`, `%` and digit-group commas are removed. `3 orders` and `3 or 4` fail |
|
|
70
|
+
| `set` | It is a list (split on commas, semicolons and new lines, or also on "and") with each value one time and nothing more, in any order |
|
|
71
|
+
| `includes` | It contains each value. An answer that names every choice also passes, so use it only where the run cannot list all choices |
|
|
72
|
+
|
|
73
|
+
A source with no rows means that the task cannot be done. Then the answer must be one of the `none` words. The default is `N/A`. A row with more than one column is one value, with the columns joined by a space.
|
|
74
|
+
|
|
75
|
+
## Write the declaration
|
|
76
|
+
|
|
77
|
+
The declaration must list every table that a run can change, or a change to that table is not seen. Do not write it by hand. Generate it, then remove the tables that change on every run:
|
|
78
|
+
|
|
79
|
+
```bash
|
|
80
|
+
# 1. One source for each table.
|
|
81
|
+
npx @reticlehq/server grade tables --container shop-db --skip queue_,cron_ --list "mysql -N shop -e 'show tables'" --rows "mysql -N shop -e 'select * from {table}'" --out wide.json
|
|
82
|
+
|
|
83
|
+
# 2. Two snapshots of the correct steps, from a reset app each time.
|
|
84
|
+
npx @reticlehq/server grade snapshot --state wide.json --out reference.json
|
|
85
|
+
npx @reticlehq/server grade snapshot --state wide.json --out again.json
|
|
86
|
+
|
|
87
|
+
# 3. Keep the tables that read the same on both runs.
|
|
88
|
+
npx @reticlehq/server grade suggest --state wide.json --reference reference.json --again again.json --out state.json
|
|
89
|
+
```
|
|
90
|
+
|
|
91
|
+
`tables` takes the first column of each line of the `--list` output as a table name. It skips a name with a character other than A-Z, 0-9, `_` or `$`, and says so. `{table}` in `--rows` is the table name.
|
|
92
|
+
|
|
93
|
+
`--skip <prefix,...>` leaves out each table whose name starts with one of the prefixes. Separate the prefixes with commas. Use it for tables that hold no task data and that the app changes at its own time: a message queue that a background worker empties, a cron schedule, a session store. Two correct runs do not always show these tables as noise, because the worker can finish before both snapshots and not before a third. For Magento, `--skip queue_,cron_,session`.
|
|
94
|
+
|
|
95
|
+
Some apps write an empty row that means the same as no row. Magento saves a product form with a `NULL` row for each empty attribute, so a run that saves the form one more time than the reference adds rows with no value. Add an `ignore` pattern that matches all of such a row to the source in `state.json`. A pattern that removes all of a row removes the row. For the Magento attribute tables (`catalog_product_entity_int`, `_decimal`, `_varchar`, `_text`, `_datetime`), use `"ignore": ["^\\d+\\t\\d+\\t\\d+\\t\\d+\\tNULL$"]`.
|
|
96
|
+
|
|
97
|
+
`suggest` keeps a source that reads the same on both runs, also a source the correct steps did not change: a change to it by a run is a change to a record the task did not name. A source that differs between the two runs only by a date and time is kept, with the time removed. Every other source that differs (a session table, a log) is dropped, because each run adds its own new rows to it, and every run would fail. Each dropped source is printed with the first row that differs. A change to a dropped table is not seen.
|
package/docs/cli/help.mdx
CHANGED
|
@@ -33,7 +33,7 @@ Get started
|
|
|
33
33
|
try Watch Reticle drive a URL once and say which journeys work
|
|
34
34
|
|
|
35
35
|
Check your app
|
|
36
|
-
verify Check
|
|
36
|
+
verify Check saved flows, or one claim with --expect, against the running app; exit 0 = pass
|
|
37
37
|
gate Fail unless passing checks cover the flows your changes touch
|
|
38
38
|
|
|
39
39
|
Reticle on this machine
|
|
@@ -85,5 +85,7 @@ Two audiences, two channels: the structured line for logs and scripts, the plain
|
|
|
85
85
|
| `1` | Help was printed because something else was wrong |
|
|
86
86
|
|
|
87
87
|
<Note>
|
|
88
|
-
A bare `reticle` with no arguments is **not** help.
|
|
88
|
+
A bare `reticle` with no arguments is **not** help. In a wired project it is [`reticle
|
|
89
|
+
serve`](/cli/serve). In a folder that Reticle has not wired, it gives a first verdict on the app:
|
|
90
|
+
see [the CLI reference](/cli).
|
|
89
91
|
</Note>
|
package/docs/cli/license.mdx
CHANGED
|
@@ -1,36 +1,37 @@
|
|
|
1
1
|
---
|
|
2
|
-
title:
|
|
3
|
-
description: Show the enterprise license status resolved from the environment, offline.
|
|
2
|
+
title: License status
|
|
3
|
+
description: Show the enterprise license status resolved from the environment, offline, with reticle status.
|
|
4
4
|
icon: key
|
|
5
5
|
---
|
|
6
6
|
|
|
7
|
-
`reticle
|
|
7
|
+
[`reticle status`](/cli/status) reports whether an enterprise license is active. It resolves the license entirely from the environment. Nothing leaves the machine.
|
|
8
8
|
|
|
9
9
|
```bash
|
|
10
|
-
npx @reticlehq/server
|
|
10
|
+
npx @reticlehq/server status --json
|
|
11
11
|
```
|
|
12
12
|
|
|
13
|
-
|
|
13
|
+
The block that `status` prints has a `license` row only when a key is set. `--json` always carries the `license` object.
|
|
14
|
+
|
|
15
|
+
`reticle license` is the old name. It still works for one release, prints one line naming `status`, and prints the `reticle_license` line below.
|
|
14
16
|
|
|
15
17
|
## What it prints
|
|
16
18
|
|
|
17
|
-
|
|
19
|
+
The `license` object of `status --json`. `reticle license` printed the same fields as one `reticle_license` JSON line on stderr. On a checkout with no issuer key configured:
|
|
18
20
|
|
|
19
21
|
```json
|
|
20
22
|
{
|
|
21
23
|
"t": "2026-08-15T18:42:26.758Z",
|
|
22
24
|
"event": "reticle_license",
|
|
23
|
-
"gated": ["audit-log"],
|
|
24
25
|
"contact": "hey@reticle.sh",
|
|
25
26
|
"status": "eval",
|
|
26
|
-
"detail": "evaluation mode
|
|
27
|
+
"detail": "evaluation mode (no issuer key configured)"
|
|
27
28
|
}
|
|
28
29
|
```
|
|
29
30
|
|
|
30
31
|
| `status` | Meaning |
|
|
31
32
|
| --------- | --------------------------------------------------- |
|
|
32
33
|
| `active` | A valid license is present |
|
|
33
|
-
| `eval` | Evaluation mode.
|
|
34
|
+
| `eval` | Evaluation mode. No issuer key is configured |
|
|
34
35
|
| `missing` | No license, and the build expects one |
|
|
35
36
|
| `expired` | The key verified, but its expiry has passed |
|
|
36
37
|
| `invalid` | The key was rejected, or the build is misconfigured |
|
|
@@ -44,9 +45,9 @@ Always `0`.
|
|
|
44
45
|
## Worked example
|
|
45
46
|
|
|
46
47
|
```bash
|
|
47
|
-
npx @reticlehq/server
|
|
48
|
+
npx @reticlehq/server status --json | jq -r .license.status
|
|
48
49
|
```
|
|
49
50
|
|
|
50
|
-
<Card title="
|
|
51
|
-
|
|
51
|
+
<Card title="Enterprise" icon="building" href="/enterprise">
|
|
52
|
+
License keys, the roadmap, and the licensing model.
|
|
52
53
|
</Card>
|
package/docs/cli/restart.mdx
CHANGED
|
@@ -1,15 +1,17 @@
|
|
|
1
1
|
---
|
|
2
|
-
title: reticle restart
|
|
2
|
+
title: reticle serve --restart
|
|
3
3
|
description: Free the bridge port and put a daemon back on it, reporting each half separately.
|
|
4
4
|
icon: rotate
|
|
5
5
|
---
|
|
6
6
|
|
|
7
|
-
`reticle restart` is [`reticle stop --force`](/cli/stop#freeing-the-port-force) followed by a daemon start that waits for a real bind.
|
|
7
|
+
`reticle serve --restart` is [`reticle stop --force`](/cli/stop#freeing-the-port-force) followed by a daemon start that waits for a real bind.
|
|
8
8
|
|
|
9
9
|
```bash
|
|
10
|
-
npx @reticlehq/server restart [--port N] [--force]
|
|
10
|
+
npx @reticlehq/server serve --restart [--port N] [--force]
|
|
11
11
|
```
|
|
12
12
|
|
|
13
|
+
`reticle restart` is the old name. It still works for one release and prints one line naming `serve --restart`.
|
|
14
|
+
|
|
13
15
|
## Flags
|
|
14
16
|
|
|
15
17
|
| Flag | Type | Default | What it does |
|
|
@@ -31,7 +33,7 @@ Real capture, restarting over a running daemon (exit `0`), with the long `note`
|
|
|
31
33
|
Real capture, when the port is held by something that is not ours (exit `1`). Both `reason` strings are trimmed at the ellipsis:
|
|
32
34
|
|
|
33
35
|
```
|
|
34
|
-
{"t":"2026-08-15T18:43:57.317Z","event":"reticle_kill_refused","port":4498,"reason":"pid 78795 (\"Python\") is listening, and it is not a Reticle daemon ... it never answered /status and it is not the pid Reticle recorded. Killing it would be killing someone else's process. If that is what you meant, `reticle restart --force` stops it and starts Reticle there (`stop --force` never does); or start Reticle on another port.","holder":"Python"}
|
|
36
|
+
{"t":"2026-08-15T18:43:57.317Z","event":"reticle_kill_refused","port":4498,"reason":"pid 78795 (\"Python\") is listening, and it is not a Reticle daemon ... it never answered /status and it is not the pid Reticle recorded. Killing it would be killing someone else's process. If that is what you meant, `reticle serve --restart --force` stops it and starts Reticle there (`stop --force` never does); or start Reticle on another port.","holder":"Python"}
|
|
35
37
|
{"t":"2026-08-15T18:43:57.318Z","event":"reticle_restart_aborted","port":4498,"reason":"the port was not freed, so nothing was started ... the old holder is still there"}
|
|
36
38
|
```
|
|
37
39
|
|
|
@@ -51,7 +53,7 @@ Real capture, when the port is held by something that is not ours (exit `1`). Bo
|
|
|
51
53
|
## Worked example
|
|
52
54
|
|
|
53
55
|
```bash
|
|
54
|
-
npx @reticlehq/server restart
|
|
56
|
+
npx @reticlehq/server serve --restart # after an upgrade, so the new version is the one serving
|
|
55
57
|
npx @reticlehq/server status
|
|
56
58
|
```
|
|
57
59
|
|
package/docs/cli/rollback.mdx
CHANGED
|
@@ -1,16 +1,16 @@
|
|
|
1
1
|
---
|
|
2
|
-
title: reticle rollback
|
|
2
|
+
title: reticle update --rollback
|
|
3
3
|
description: Reinstall the previously installed Reticle server version, then exit so your agent restarts it.
|
|
4
4
|
icon: arrow-rotate-left
|
|
5
5
|
---
|
|
6
6
|
|
|
7
|
-
`reticle rollback` is the undo for [`reticle update`](/cli/update). It reinstalls the version `update` replaced (recorded in the update manifest), then exits so the next start runs it.
|
|
7
|
+
`reticle update --rollback` is the undo for [`reticle update`](/cli/update). It reinstalls the version `update` replaced (recorded in the update manifest), then exits so the next start runs it.
|
|
8
8
|
|
|
9
9
|
```bash
|
|
10
|
-
npx @reticlehq/server rollback
|
|
10
|
+
npx @reticlehq/server update --rollback
|
|
11
11
|
```
|
|
12
12
|
|
|
13
|
-
|
|
13
|
+
`reticle rollback` is the old name. It still works for one release and prints one line naming `update --rollback`.
|
|
14
14
|
|
|
15
15
|
## What it prints
|
|
16
16
|
|
|
@@ -36,6 +36,6 @@ On the global install the installer puts on your PATH (under `npx` there is noth
|
|
|
36
36
|
```text
|
|
37
37
|
reticle update
|
|
38
38
|
# the new build misbehaves:
|
|
39
|
-
reticle rollback
|
|
39
|
+
reticle update --rollback
|
|
40
40
|
reticle version
|
|
41
41
|
```
|
package/docs/cli/setup.mdx
CHANGED
|
@@ -14,10 +14,21 @@ No flags, and nothing is asked. It works for your user account, not for one proj
|
|
|
14
14
|
|
|
15
15
|
## What it prints
|
|
16
16
|
|
|
17
|
-
|
|
17
|
+
A `Your agents:` block, with one line for each agent and the one next step for that agent:
|
|
18
|
+
|
|
19
|
+
```text
|
|
20
|
+
Your agents:
|
|
21
|
+
Claude Code plugin active: type /reload-plugins if it is open
|
|
22
|
+
Cursor added: restart Cursor, then turn Reticle on in Settings › MCP
|
|
23
|
+
Codex added: restart Codex, then /mcp shows reticle
|
|
24
|
+
```
|
|
25
|
+
|
|
26
|
+
`already set up` means that Reticle was there already. `registration failed` gives the command to retry, and the command then exits `1`. `not added: add the reticle entry to <path> by hand` is for a config that it does not rewrite. If it finds no agent, it names every agent it looked for.
|
|
27
|
+
|
|
28
|
+
In a terminal, and not in CI, it then waits up to 60 seconds for each agent to connect. Then it prints `Connected: <agent> ✓`, or the step that is still missing for that agent. Press Ctrl+C to stop the wait. [`reticle status`](/cli/status) shows the same lines later.
|
|
18
29
|
|
|
19
30
|
## How you know it worked
|
|
20
31
|
|
|
21
|
-
|
|
32
|
+
Do the next step for your agent. Most agents read their server list only when they start. The Claude Code plugin loads with `/reload-plugins`. Then the `reticle_*` tools are listed, and `reticle status` shows `Connected: <agent> ✓`.
|
|
22
33
|
|
|
23
34
|
Codex CLI keeps a TOML config. When the `codex` binary is on your PATH, Reticle registers through `codex mcp add`. Otherwise it prints the hand-edit lines above. Reticle then adds one line, `default_tools_approval_mode = "approve"`, under `[mcp_servers.reticle]` in `~/.codex/config.toml`. This line approves Reticle's own tools, so Codex does not ask before each call. Reticle changes no other line, and it keeps a mode that you set. To undo it, change that line to `default_tools_approval_mode = "prompt"`. Reticle does not change a mode that is already there.
|
package/docs/cli/status.mdx
CHANGED
|
@@ -35,8 +35,12 @@ reticle status
|
|
|
35
35
|
http://localhost:5173/ (throttled, hidden)
|
|
36
36
|
http://localhost:7699/ (throttled, hidden)
|
|
37
37
|
agent link ✓ your agent has read and used Reticle's tools
|
|
38
|
+
agents Connected: Claude Code ✓
|
|
39
|
+
Cursor not connected yet: restart Cursor, then turn Reticle on in Settings › MCP
|
|
38
40
|
```
|
|
39
41
|
|
|
42
|
+
The `agents` row has one line for each coding agent on this machine. A line shows `✓` when that agent connected to Reticle at least one time. Otherwise it shows the step that is still missing. `reticle setup mcp` prints the same lines.
|
|
43
|
+
|
|
40
44
|
And with no daemon on the port:
|
|
41
45
|
|
|
42
46
|
```text
|