@phnx-labs/agents-cli 1.22.34 → 1.22.37
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/CHANGELOG.md +672 -2
- package/README.md +82 -35
- package/dist/bin/agents +0 -0
- package/dist/bootstrap.d.ts +15 -0
- package/dist/bootstrap.js +1211 -0
- package/dist/commands/accounts.d.ts +4 -11
- package/dist/commands/accounts.js +159 -27
- package/dist/commands/attach.js +17 -4
- package/dist/commands/audit.d.ts +8 -8
- package/dist/commands/audit.js +57 -47
- package/dist/commands/browser.js +15 -11
- package/dist/commands/cloud.js +1 -1
- package/dist/commands/commands.js +0 -11
- package/dist/commands/computer-actions.js +33 -0
- package/dist/commands/computer-sessions-picker.d.ts +21 -0
- package/dist/commands/computer-sessions-picker.js +141 -0
- package/dist/commands/computer.d.ts +16 -0
- package/dist/commands/computer.js +37 -0
- package/dist/commands/config.d.ts +17 -0
- package/dist/commands/config.js +401 -0
- package/dist/commands/cp.d.ts +84 -0
- package/dist/commands/cp.js +231 -0
- package/dist/commands/daemon.js +243 -14
- package/dist/commands/detach-core.d.ts +1 -1
- package/dist/commands/detach-core.js +12 -2
- package/dist/commands/detach.js +1 -1
- package/dist/commands/doctor.js +64 -5
- package/dist/commands/events.d.ts +24 -12
- package/dist/commands/events.js +144 -28
- package/dist/commands/exec.js +85 -41
- package/dist/commands/feed.d.ts +1 -1
- package/dist/commands/feed.js +16 -8
- package/dist/commands/focus.d.ts +33 -1
- package/dist/commands/focus.js +177 -17
- package/dist/commands/funnel.d.ts +1 -1
- package/dist/commands/go.js +9 -8
- package/dist/commands/harness-wizard.d.ts +1 -0
- package/dist/commands/harness-wizard.js +18 -20
- package/dist/commands/harness.d.ts +2 -0
- package/dist/commands/harness.js +59 -26
- package/dist/commands/hooks.js +0 -11
- package/dist/commands/inspect.d.ts +94 -1
- package/dist/commands/inspect.js +866 -40
- package/dist/commands/lease.d.ts +4 -4
- package/dist/commands/lease.js +6 -6
- package/dist/commands/login.js +0 -13
- package/dist/commands/logs.d.ts +2 -2
- package/dist/commands/logs.js +2 -2
- package/dist/commands/mcp.js +7 -2
- package/dist/commands/memory.js +7 -2
- package/dist/commands/message.d.ts +1 -1
- package/dist/commands/message.js +37 -6
- package/dist/commands/models.js +4 -0
- package/dist/commands/monitors.d.ts +0 -1
- package/dist/commands/monitors.js +199 -16
- package/dist/commands/open.d.ts +18 -0
- package/dist/commands/open.js +57 -0
- package/dist/commands/packages.js +2 -107
- package/dist/commands/plugins.js +6 -3
- package/dist/commands/profiles.d.ts +1 -0
- package/dist/commands/profiles.js +16 -160
- package/dist/commands/projects.d.ts +28 -0
- package/dist/commands/projects.js +125 -5
- package/dist/commands/reconnect.js +9 -3
- package/dist/commands/repo.js +42 -1
- package/dist/commands/resource-view.d.ts +17 -0
- package/dist/commands/resource-view.js +36 -14
- package/dist/commands/resume.js +9 -2
- package/dist/commands/routines.d.ts +0 -2
- package/dist/commands/routines.js +473 -289
- package/dist/commands/secrets.js +52 -9
- package/dist/commands/sessions-export.d.ts +47 -0
- package/dist/commands/sessions-export.js +116 -6
- package/dist/commands/sessions-import.d.ts +17 -0
- package/dist/commands/sessions-import.js +114 -6
- package/dist/commands/sessions-migrate.d.ts +27 -0
- package/dist/commands/sessions-migrate.js +50 -9
- package/dist/commands/sessions-picker.js +23 -4
- package/dist/commands/sessions-resume.d.ts +5 -3
- package/dist/commands/sessions-resume.js +30 -8
- package/dist/commands/sessions-watch.d.ts +2 -0
- package/dist/commands/sessions-watch.js +53 -0
- package/dist/commands/sessions.d.ts +66 -3
- package/dist/commands/sessions.js +298 -47
- package/dist/commands/set.d.ts +1 -1
- package/dist/commands/set.js +2 -2
- package/dist/commands/setup-browser.js +2 -2
- package/dist/commands/setup-mine.js +0 -1
- package/dist/commands/setup-preferences.js +1 -1
- package/dist/commands/setup-share.js +34 -4
- package/dist/commands/setup.d.ts +5 -0
- package/dist/commands/setup.js +26 -0
- package/dist/commands/share.d.ts +85 -0
- package/dist/commands/share.js +379 -8
- package/dist/commands/skills.js +0 -11
- package/dist/commands/snapshot.js +1 -1
- package/dist/commands/ssh.d.ts +18 -0
- package/dist/commands/ssh.js +549 -210
- package/dist/commands/sync.d.ts +5 -0
- package/dist/commands/sync.js +212 -32
- package/dist/commands/teams.d.ts +13 -0
- package/dist/commands/teams.js +187 -30
- package/dist/commands/tickets.d.ts +2 -0
- package/dist/commands/tickets.js +43 -0
- package/dist/commands/update.js +2 -4
- package/dist/commands/usage.js +5 -3
- package/dist/commands/versions.js +11 -5
- package/dist/commands/view.js +15 -7
- package/dist/commands/webhook.d.ts +2 -2
- package/dist/commands/webhook.js +7 -7
- package/dist/index.d.ts +18 -2
- package/dist/index.js +53 -1264
- package/dist/lib/account-catalog.d.ts +18 -0
- package/dist/lib/account-catalog.js +38 -0
- package/dist/lib/account-provider-registry.d.ts +18 -0
- package/dist/lib/account-provider-registry.js +59 -0
- package/dist/lib/account-registry.d.ts +40 -0
- package/dist/lib/account-registry.js +239 -0
- package/dist/lib/account-schema.d.ts +44 -0
- package/dist/lib/account-schema.js +91 -0
- package/dist/lib/account-state-service.d.ts +21 -0
- package/dist/lib/account-state-service.js +60 -0
- package/dist/lib/activity.d.ts +1 -1
- package/dist/lib/activity.js +8 -1
- package/dist/lib/add-dir.d.ts +80 -0
- package/dist/lib/add-dir.js +241 -0
- package/dist/lib/agent-cli-commands.d.ts +11 -0
- package/dist/lib/agent-cli-commands.js +30 -0
- package/dist/lib/agents.js +44 -36
- package/dist/lib/answer-router.js +1 -1
- package/dist/lib/audit/log.d.ts +10 -27
- package/dist/lib/audit/log.js +20 -33
- package/dist/lib/auth-health.d.ts +9 -2
- package/dist/lib/auth-health.js +42 -9
- package/dist/lib/auto-pull-worker.js +7 -3
- package/dist/lib/auto-pull.d.ts +44 -3
- package/dist/lib/auto-pull.js +88 -5
- package/dist/lib/binary-shadow.d.ts +28 -0
- package/dist/lib/binary-shadow.js +121 -0
- package/dist/lib/brand.js +9 -3
- package/dist/lib/browser/ipc.d.ts +30 -0
- package/dist/lib/browser/ipc.js +81 -4
- package/dist/lib/browser/profiles.d.ts +3 -2
- package/dist/lib/browser/profiles.js +65 -22
- package/dist/lib/browser/service.d.ts +4 -0
- package/dist/lib/browser/service.js +30 -3
- package/dist/lib/browser/sessions-list.d.ts +22 -2
- package/dist/lib/browser/sessions-list.js +54 -6
- package/dist/lib/browser/stream.d.ts +2 -0
- package/dist/lib/browser/stream.js +1 -0
- package/dist/lib/browser/types.d.ts +19 -0
- package/dist/lib/byok-usage.d.ts +9 -2
- package/dist/lib/byok-usage.js +133 -31
- package/dist/lib/cli-entry.d.ts +11 -0
- package/dist/lib/cli-entry.js +46 -0
- package/dist/lib/cloud/host.d.ts +1 -1
- package/dist/lib/cloud/host.js +2 -2
- package/dist/lib/cloud/registry.js +1 -1
- package/dist/lib/cloud/types.d.ts +1 -1
- package/dist/lib/codex-policy.d.ts +9 -1
- package/dist/lib/codex-policy.js +17 -2
- package/dist/lib/commands.d.ts +2 -0
- package/dist/lib/commands.js +2 -0
- package/dist/lib/computer/sessions-list.d.ts +150 -0
- package/dist/lib/computer/sessions-list.js +363 -0
- package/dist/lib/config-keys.d.ts +86 -0
- package/dist/lib/config-keys.js +193 -0
- package/dist/lib/config-machine-keys.d.ts +12 -0
- package/dist/lib/config-machine-keys.js +17 -0
- package/dist/lib/config-transfer.js +3 -4
- package/dist/lib/crabbox/cli.d.ts +2 -2
- package/dist/lib/crabbox/cli.js +3 -3
- package/dist/lib/daemon-health.d.ts +22 -0
- package/dist/lib/daemon-health.js +33 -3
- package/dist/lib/daemon-services.d.ts +50 -0
- package/dist/lib/daemon-services.js +147 -0
- package/dist/lib/daemon-ticks.d.ts +35 -66
- package/dist/lib/daemon-ticks.js +77 -159
- package/dist/lib/daemon.d.ts +72 -4
- package/dist/lib/daemon.js +792 -202
- package/dist/lib/deeplink/register.d.ts +49 -0
- package/dist/lib/deeplink/register.js +253 -0
- package/dist/lib/deeplink/url.d.ts +34 -0
- package/dist/lib/deeplink/url.js +78 -0
- package/dist/lib/device-config.d.ts +124 -29
- package/dist/lib/device-config.js +346 -141
- package/dist/lib/devices/config-migration.d.ts +42 -0
- package/dist/lib/devices/config-migration.js +203 -0
- package/dist/lib/devices/connect.js +14 -7
- package/dist/lib/devices/doctor-findings.d.ts +4 -1
- package/dist/lib/devices/doctor-findings.js +20 -1
- package/dist/lib/devices/harness-inventory.d.ts +11 -2
- package/dist/lib/devices/harness-inventory.js +0 -0
- package/dist/lib/devices/health.d.ts +1 -1
- package/dist/lib/devices/health.js +1 -1
- package/dist/lib/devices/pending.d.ts +22 -1
- package/dist/lib/devices/pending.js +67 -2
- package/dist/lib/devices/registry.d.ts +0 -25
- package/dist/lib/devices/registry.js +2 -83
- package/dist/lib/devices/resolve-profile.d.ts +20 -0
- package/dist/lib/devices/resolve-profile.js +44 -0
- package/dist/lib/devices/rollout-verify.d.ts +101 -0
- package/dist/lib/devices/rollout-verify.js +193 -0
- package/dist/lib/devices/ssh-config.js +10 -6
- package/dist/lib/event-families.d.ts +28 -0
- package/dist/lib/event-families.js +159 -0
- package/dist/lib/event-stream.d.ts +9 -1
- package/dist/lib/event-stream.js +26 -9
- package/dist/lib/events.d.ts +9 -1
- package/dist/lib/events.js +21 -6
- package/dist/lib/exec.d.ts +30 -0
- package/dist/lib/exec.js +220 -122
- package/dist/lib/feed-broadcast.d.ts +25 -0
- package/dist/lib/feed-broadcast.js +33 -0
- package/dist/lib/feed.d.ts +1 -1
- package/dist/lib/feed.js +12 -2
- package/dist/lib/fleet/capture.js +15 -0
- package/dist/lib/fleet/manifest.js +9 -0
- package/dist/lib/fleet/types.d.ts +9 -0
- package/dist/lib/fleet-status.js +10 -8
- package/dist/lib/git.d.ts +20 -6
- package/dist/lib/git.js +121 -17
- package/dist/lib/hosts/dispatch.d.ts +8 -3
- package/dist/lib/hosts/dispatch.js +29 -3
- package/dist/lib/hosts/logs.d.ts +2 -2
- package/dist/lib/hosts/logs.js +2 -2
- package/dist/lib/hosts/option.js +1 -1
- package/dist/lib/hosts/passthrough.d.ts +2 -3
- package/dist/lib/hosts/passthrough.js +10 -24
- package/dist/lib/hosts/progress.js +2 -2
- package/dist/lib/hosts/providers/devices.d.ts +3 -3
- package/dist/lib/hosts/providers/devices.js +18 -12
- package/dist/lib/hosts/ready.d.ts +5 -1
- package/dist/lib/hosts/ready.js +9 -3
- package/dist/lib/hosts/reconcile.d.ts +2 -2
- package/dist/lib/hosts/reconcile.js +2 -2
- package/dist/lib/hosts/registry.js +14 -9
- package/dist/lib/hosts/remote-cmd.js +1 -1
- package/dist/lib/hosts/remote-os.d.ts +9 -6
- package/dist/lib/hosts/remote-os.js +13 -6
- package/dist/lib/hosts/routing-flag.d.ts +23 -0
- package/dist/lib/hosts/routing-flag.js +41 -0
- package/dist/lib/hosts/run-target.js +1 -1
- package/dist/lib/hosts/session-index.js +1 -1
- package/dist/lib/hosts/tasks.d.ts +6 -6
- package/dist/lib/hosts/tasks.js +4 -4
- package/dist/lib/hosts/types.js +1 -2
- package/dist/lib/installations/resolve.js +2 -8
- package/dist/lib/isolation-boundary-report.js +0 -1
- package/dist/lib/linear-cache.d.ts +7 -0
- package/dist/lib/linear-cache.js +31 -4
- package/dist/lib/linear-project-counts.d.ts +1 -1
- package/dist/lib/linear-project-counts.js +2 -3
- package/dist/lib/linear-projects.js +1 -1
- package/dist/lib/loop.d.ts +2 -2
- package/dist/lib/loop.js +1 -1
- package/dist/lib/mailbox-target.d.ts +1 -1
- package/dist/lib/mailbox-target.js +1 -1
- package/dist/lib/manifest.js +7 -4
- package/dist/lib/menubar/MenubarHelper.app/Contents/CodeResources +0 -0
- package/dist/lib/menubar/MenubarHelper.app/Contents/MacOS/MenubarHelper +0 -0
- package/dist/lib/menubar/snapshot.d.ts +3 -2
- package/dist/lib/menubar/snapshot.js +6 -2
- package/dist/lib/migrate-fold.d.ts +33 -0
- package/dist/lib/migrate-fold.js +130 -0
- package/dist/lib/migrate.d.ts +34 -34
- package/dist/lib/migrate.js +106 -128
- package/dist/lib/model-tier-overrides.d.ts +1 -1
- package/dist/lib/model-tier-overrides.js +15 -2
- package/dist/lib/monitors/config.d.ts +17 -3
- package/dist/lib/monitors/config.js +52 -18
- package/dist/lib/monitors/engine.d.ts +32 -1
- package/dist/lib/monitors/engine.js +94 -11
- package/dist/lib/monitors/fingerprint.d.ts +46 -0
- package/dist/lib/monitors/fingerprint.js +100 -0
- package/dist/lib/monitors/remote.d.ts +47 -0
- package/dist/lib/monitors/remote.js +81 -0
- package/dist/lib/monitors/state.d.ts +39 -0
- package/dist/lib/monitors/state.js +56 -0
- package/dist/lib/onepassword.d.ts +17 -0
- package/dist/lib/onepassword.js +52 -22
- package/dist/lib/open-url.js +1 -1
- package/dist/lib/picker.d.ts +14 -2
- package/dist/lib/picker.js +35 -13
- package/dist/lib/placement.d.ts +1 -1
- package/dist/lib/placement.js +1 -1
- package/dist/lib/pr-land-detach.d.ts +32 -0
- package/dist/lib/pr-land-detach.js +79 -0
- package/dist/lib/profiles-presets.js +13 -0
- package/dist/lib/profiles.d.ts +2 -0
- package/dist/lib/profiles.js +44 -1
- package/dist/lib/project-focus.d.ts +1 -1
- package/dist/lib/project-focus.js +1 -1
- package/dist/lib/project-key.d.ts +17 -0
- package/dist/lib/project-key.js +26 -0
- package/dist/lib/project-probe.d.ts +4 -1
- package/dist/lib/project-probe.js +5 -4
- package/dist/lib/project-resources.js +2 -18
- package/dist/lib/project-root.d.ts +16 -0
- package/dist/lib/project-root.js +20 -2
- package/dist/lib/projects.d.ts +20 -1
- package/dist/lib/projects.js +78 -1
- package/dist/lib/refresh-coordinator.d.ts +24 -0
- package/dist/lib/refresh-coordinator.js +52 -0
- package/dist/lib/registry.d.ts +2 -2
- package/dist/lib/registry.js +1 -1
- package/dist/lib/resource-aliases.d.ts +13 -0
- package/dist/lib/resource-aliases.js +26 -0
- package/dist/lib/resources/types.d.ts +1 -1
- package/dist/lib/resources.d.ts +16 -0
- package/dist/lib/resources.js +66 -10
- package/dist/lib/rotate.d.ts +3 -4
- package/dist/lib/rotate.js +4 -5
- package/dist/lib/routine-activation.d.ts +22 -2
- package/dist/lib/routine-activation.js +63 -16
- package/dist/lib/routine-context.d.ts +9 -2
- package/dist/lib/routine-context.js +21 -6
- package/dist/lib/routines-project.d.ts +58 -48
- package/dist/lib/routines-project.js +190 -159
- package/dist/lib/routines.d.ts +41 -6
- package/dist/lib/routines.js +92 -34
- package/dist/lib/run-defaults.d.ts +5 -0
- package/dist/lib/run-defaults.js +11 -1
- package/dist/lib/runner.d.ts +10 -8
- package/dist/lib/runner.js +122 -39
- package/dist/lib/secrets/Agents CLI.app/Contents/CodeResources +0 -0
- package/dist/lib/secrets/Agents CLI.app/Contents/MacOS/Agents CLI +0 -0
- package/dist/lib/secrets/agent.d.ts +10 -3
- package/dist/lib/secrets/agent.js +43 -8
- package/dist/lib/secrets/bundles.d.ts +1 -0
- package/dist/lib/secrets/bundles.js +92 -80
- package/dist/lib/secrets/index.js +32 -9
- package/dist/lib/secrets/install-helper.d.ts +4 -4
- package/dist/lib/secrets/install-helper.js +4 -4
- package/dist/lib/secrets/push.d.ts +40 -6
- package/dist/lib/secrets/push.js +58 -11
- package/dist/lib/secrets/read-backoff.d.ts +1 -1
- package/dist/lib/secrets/read-backoff.js +1 -1
- package/dist/lib/secrets/remote.d.ts +24 -0
- package/dist/lib/secrets/remote.js +54 -4
- package/dist/lib/self-update.d.ts +108 -0
- package/dist/lib/self-update.js +276 -1
- package/dist/lib/session/active.d.ts +89 -5
- package/dist/lib/session/active.js +165 -10
- package/dist/lib/session/actor-sidecar.d.ts +1 -1
- package/dist/lib/session/actor-sidecar.js +2 -1
- package/dist/lib/session/db.d.ts +176 -2
- package/dist/lib/session/db.js +484 -17
- package/dist/lib/session/discover.js +27 -4
- package/dist/lib/session/hook-sessions.js +2 -2
- package/dist/lib/session/host-link.d.ts +2 -2
- package/dist/lib/session/host-link.js +2 -2
- package/dist/lib/session/pid-registry.d.ts +21 -0
- package/dist/lib/session/pid-registry.js +57 -0
- package/dist/lib/session/remote-active.js +15 -1
- package/dist/lib/session/remote.js +2 -2
- package/dist/lib/session/session-cache.d.ts +14 -7
- package/dist/lib/session/session-cache.js +51 -9
- package/dist/lib/session/state.d.ts +2 -2
- package/dist/lib/session/state.js +1 -1
- package/dist/lib/session/sync/config.d.ts +10 -10
- package/dist/lib/session/sync/config.js +10 -10
- package/dist/lib/session/sync/r2.d.ts +34 -0
- package/dist/lib/session/sync/r2.js +123 -0
- package/dist/lib/session/throughput.d.ts +1 -1
- package/dist/lib/session/throughput.js +1 -1
- package/dist/lib/session/types.d.ts +23 -1
- package/dist/lib/session/types.js +15 -0
- package/dist/lib/session/viewing-in.d.ts +1 -1
- package/dist/lib/session/viewing-in.js +1 -1
- package/dist/lib/session/watch.d.ts +101 -0
- package/dist/lib/session/watch.js +242 -0
- package/dist/lib/share/config.d.ts +4 -0
- package/dist/lib/share/config.js +1 -0
- package/dist/lib/share/delete.d.ts +93 -0
- package/dist/lib/share/delete.js +127 -0
- package/dist/lib/share/provision.d.ts +38 -0
- package/dist/lib/share/provision.js +50 -0
- package/dist/lib/share/publish.d.ts +40 -1
- package/dist/lib/share/publish.js +116 -3
- package/dist/lib/share/worker-template.js +71 -6
- package/dist/lib/shims.d.ts +17 -3
- package/dist/lib/shims.js +136 -27
- package/dist/lib/signin-badge.js +3 -2
- package/dist/lib/skills.js +2 -0
- package/dist/lib/smart-launch.d.ts +8 -8
- package/dist/lib/smart-launch.js +80 -59
- package/dist/lib/ssh-exec.d.ts +1 -1
- package/dist/lib/ssh-exec.js +1 -1
- package/dist/lib/staleness/prune.d.ts +88 -0
- package/dist/lib/staleness/prune.js +69 -0
- package/dist/lib/staleness/registry.d.ts +1 -1
- package/dist/lib/staleness/writers/commands.js +34 -2
- package/dist/lib/staleness/writers/hooks.js +16 -0
- package/dist/lib/staleness/writers/kinds.d.ts +6 -0
- package/dist/lib/staleness/writers/skills.js +19 -0
- package/dist/lib/staleness/writers/subagents.d.ts +2 -3
- package/dist/lib/staleness/writers/subagents.js +0 -4
- package/dist/lib/staleness/writers/types.d.ts +32 -0
- package/dist/lib/startup/command-registry.d.ts +6 -12
- package/dist/lib/startup/command-registry.js +14 -31
- package/dist/lib/startup/dev-build.d.ts +10 -0
- package/dist/lib/startup/dev-build.js +13 -1
- package/dist/lib/startup/spellcheck.d.ts +18 -0
- package/dist/lib/startup/spellcheck.js +45 -0
- package/dist/lib/state.d.ts +36 -9
- package/dist/lib/state.js +96 -46
- package/dist/lib/subagents-registry.d.ts +0 -7
- package/dist/lib/subagents-registry.js +38 -65
- package/dist/lib/subagents.d.ts +0 -33
- package/dist/lib/subagents.js +0 -75
- package/dist/lib/sync-umbrella.js +1 -1
- package/dist/lib/teams/agents.d.ts +41 -1
- package/dist/lib/teams/agents.js +187 -9
- package/dist/lib/teams/api.d.ts +11 -1
- package/dist/lib/teams/api.js +11 -2
- package/dist/lib/teams/delivery.d.ts +41 -0
- package/dist/lib/teams/delivery.js +60 -0
- package/dist/lib/teams/registry.d.ts +14 -0
- package/dist/lib/teams/registry.js +51 -1
- package/dist/lib/teams/remoteWorktree.d.ts +19 -0
- package/dist/lib/teams/remoteWorktree.js +29 -0
- package/dist/lib/teams/scheduler.d.ts +1 -1
- package/dist/lib/teams/scheduler.js +1 -1
- package/dist/lib/teams/worktree.d.ts +24 -0
- package/dist/lib/teams/worktree.js +42 -0
- package/dist/lib/terminal/backends/vscodium-agent.d.ts +10 -1
- package/dist/lib/terminal/backends/vscodium-agent.js +16 -5
- package/dist/lib/terminal/engine.d.ts +4 -0
- package/dist/lib/terminal/engine.js +8 -2
- package/dist/lib/terminal/types.d.ts +21 -2
- package/dist/lib/testdata/refresh-coordinator-worker.d.ts +1 -0
- package/dist/lib/testdata/refresh-coordinator-worker.js +23 -0
- package/dist/lib/tickets/list.d.ts +53 -0
- package/dist/lib/tickets/list.js +153 -0
- package/dist/lib/tmux/orphan-reap.d.ts +320 -0
- package/dist/lib/tmux/orphan-reap.js +644 -0
- package/dist/lib/tmux/session.d.ts +68 -3
- package/dist/lib/tmux/session.js +95 -5
- package/dist/lib/triggers/handlers.d.ts +20 -0
- package/dist/lib/triggers/handlers.js +6 -1
- package/dist/lib/types.d.ts +46 -34
- package/dist/lib/usage-fleet.d.ts +32 -0
- package/dist/lib/usage-fleet.js +125 -0
- package/dist/lib/usage-refresh.d.ts +3 -3
- package/dist/lib/usage-refresh.js +19 -16
- package/dist/lib/usage.d.ts +51 -47
- package/dist/lib/usage.js +145 -153
- package/dist/lib/version-duplicates.js +2 -2
- package/dist/lib/versions.d.ts +56 -13
- package/dist/lib/versions.js +195 -45
- package/dist/lib/watchdog/log.d.ts +1 -1
- package/dist/lib/watchdog/log.js +3 -3
- package/dist/lib/watchdog/rotate.d.ts +6 -6
- package/dist/lib/watchdog/rotate.js +6 -6
- package/dist/lib/workflows.d.ts +1 -1
- package/dist/lib/yaml-io.d.ts +47 -0
- package/dist/lib/yaml-io.js +55 -0
- package/package.json +2 -1
- package/scripts/install-helper.js +2 -2
- package/scripts/postinstall.js +23 -20
- package/dist/commands/defaults.d.ts +0 -7
- package/dist/commands/defaults.js +0 -107
- package/dist/commands/export.d.ts +0 -11
- package/dist/commands/export.js +0 -215
- package/dist/commands/helper.d.ts +0 -12
- package/dist/commands/helper.js +0 -87
- package/dist/commands/hosts.d.ts +0 -11
- package/dist/commands/hosts.js +0 -330
- package/dist/commands/lock.d.ts +0 -12
- package/dist/commands/lock.js +0 -70
- package/dist/commands/pull.d.ts +0 -17
- package/dist/commands/pull.js +0 -39
- package/dist/commands/push.d.ts +0 -14
- package/dist/commands/push.js +0 -30
- package/dist/commands/wallet.d.ts +0 -20
- package/dist/commands/wallet.js +0 -216
- package/dist/commands/worktree.d.ts +0 -19
- package/dist/commands/worktree.js +0 -272
- package/dist/lib/account-labels.d.ts +0 -24
- package/dist/lib/account-labels.js +0 -72
- package/dist/lib/auto-dispatch-linear.d.ts +0 -18
- package/dist/lib/auto-dispatch-linear.js +0 -107
- package/dist/lib/auto-dispatch-provider.d.ts +0 -10
- package/dist/lib/auto-dispatch-provider.js +0 -30
- package/dist/lib/auto-dispatch.d.ts +0 -93
- package/dist/lib/auto-dispatch.js +0 -128
- package/dist/lib/export.d.ts +0 -72
- package/dist/lib/export.js +0 -269
- package/dist/lib/lock.d.ts +0 -93
- package/dist/lib/lock.js +0 -207
- package/dist/lib/wallet/index.d.ts +0 -78
- package/dist/lib/wallet/index.js +0 -253
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
export declare const AGENTS_URL_SCHEME = "agents";
|
|
2
|
+
export declare const MAC_BUNDLE_ID = "dev.agents.urlhandler";
|
|
3
|
+
export interface SchemeStatus {
|
|
4
|
+
registered: boolean;
|
|
5
|
+
platform: NodeJS.Platform;
|
|
6
|
+
/** One human line: where the handler is, or why it is not registered. */
|
|
7
|
+
detail: string;
|
|
8
|
+
}
|
|
9
|
+
/**
|
|
10
|
+
* POSIX single-quote a path so a space or metacharacter in it can never break
|
|
11
|
+
* out of the handler command.
|
|
12
|
+
*/
|
|
13
|
+
export declare function shQuote(p: string): string;
|
|
14
|
+
/**
|
|
15
|
+
* Resolve how the OS handler should invoke this CLI, as an already-quoted
|
|
16
|
+
* command prefix (without the `open <url>` suffix).
|
|
17
|
+
*
|
|
18
|
+
* A macOS GUI app does NOT inherit the shell PATH, so the handler must use an
|
|
19
|
+
* absolute path. Prefer the `agents` shim on PATH (directly executable); fall
|
|
20
|
+
* back to `<node> <entry>` for a bare JS install.
|
|
21
|
+
*/
|
|
22
|
+
export declare function resolveAgentsInvocation(platform?: NodeJS.Platform): string;
|
|
23
|
+
/** The freedesktop `.desktop` entry that claims `x-scheme-handler/agents`. */
|
|
24
|
+
export declare function linuxDesktopEntry(invocation: string): string;
|
|
25
|
+
/**
|
|
26
|
+
* AppleScript whose `on open location` handler fires when macOS routes an
|
|
27
|
+
* `agents://` URL to the app. `quoted form of` makes the URL a single safe
|
|
28
|
+
* shell argument — the URL is never concatenated unquoted.
|
|
29
|
+
*/
|
|
30
|
+
export declare function macAppleScriptSource(invocation: string): string;
|
|
31
|
+
/** PlistBuddy commands that add the `agents` URL type to a compiled app's Info.plist. */
|
|
32
|
+
export declare function macPlistBuddyCommands(plistPath: string): string[][];
|
|
33
|
+
/** `reg add` argv lists that register the scheme under HKCU on Windows. */
|
|
34
|
+
export declare function windowsRegistryCommands(invocation: string): string[][];
|
|
35
|
+
export declare function linuxDesktopPath(home?: string): string;
|
|
36
|
+
export declare function macAppPath(home?: string): string;
|
|
37
|
+
/** Whether the handler artifact exists on disk (a cheap, side-effect-free check). */
|
|
38
|
+
export declare function agentsUrlSchemeStatus(platform?: NodeJS.Platform, home?: string): SchemeStatus;
|
|
39
|
+
export interface RegisterOptions {
|
|
40
|
+
platform?: NodeJS.Platform;
|
|
41
|
+
home?: string;
|
|
42
|
+
/** Skip if already present (used by best-effort callers like setup). */
|
|
43
|
+
ifMissing?: boolean;
|
|
44
|
+
}
|
|
45
|
+
export declare function registerAgentsUrlScheme(opts?: RegisterOptions): SchemeStatus;
|
|
46
|
+
export declare function unregisterAgentsUrlScheme(opts?: {
|
|
47
|
+
platform?: NodeJS.Platform;
|
|
48
|
+
home?: string;
|
|
49
|
+
}): SchemeStatus;
|
|
@@ -0,0 +1,253 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Register the `agents://` URL scheme with the OS so a click in an artifact
|
|
3
|
+
* routes to `agents open <url>` (see url.ts + commands/open.ts).
|
|
4
|
+
*
|
|
5
|
+
* A browser page cannot spawn a shell; a registered URL scheme is the
|
|
6
|
+
* OS-sanctioned hand-off. Each platform gets its own handler:
|
|
7
|
+
* - Linux: a `.desktop` entry claiming `x-scheme-handler/agents`, made the
|
|
8
|
+
* default via `xdg-mime`.
|
|
9
|
+
* - macOS: a tiny AppleScript app whose `on open location` runs the CLI;
|
|
10
|
+
* its Info.plist declares the `agents` scheme, registered with
|
|
11
|
+
* LaunchServices via `lsregister`.
|
|
12
|
+
* - Windows: `HKCU\Software\Classes\agents` shell-open-command registry keys.
|
|
13
|
+
*
|
|
14
|
+
* The content generators below are pure and unit-tested. The `register*` /
|
|
15
|
+
* `unregister*` / `status*` functions apply them and never throw — they return a
|
|
16
|
+
* {@link SchemeStatus} so callers (setup, `agents open register`, doctor) can
|
|
17
|
+
* report without a try/catch.
|
|
18
|
+
*/
|
|
19
|
+
import { execFileSync } from 'node:child_process';
|
|
20
|
+
import * as fs from 'node:fs';
|
|
21
|
+
import * as os from 'node:os';
|
|
22
|
+
import * as path from 'node:path';
|
|
23
|
+
import { getAgentsBinPath } from '../cli-entry.js';
|
|
24
|
+
export const AGENTS_URL_SCHEME = 'agents';
|
|
25
|
+
export const MAC_BUNDLE_ID = 'dev.agents.urlhandler';
|
|
26
|
+
const LINUX_DESKTOP_FILE = 'agents-url-handler.desktop';
|
|
27
|
+
const MAC_APP_NAME = 'AgentsURLHandler.app';
|
|
28
|
+
// ---------------------------------------------------------------------------
|
|
29
|
+
// Invocation resolution — the absolute command the handler runs.
|
|
30
|
+
// ---------------------------------------------------------------------------
|
|
31
|
+
/**
|
|
32
|
+
* POSIX single-quote a path so a space or metacharacter in it can never break
|
|
33
|
+
* out of the handler command.
|
|
34
|
+
*/
|
|
35
|
+
export function shQuote(p) {
|
|
36
|
+
return `'${p.replace(/'/g, `'\\''`)}'`;
|
|
37
|
+
}
|
|
38
|
+
/**
|
|
39
|
+
* Resolve how the OS handler should invoke this CLI, as an already-quoted
|
|
40
|
+
* command prefix (without the `open <url>` suffix).
|
|
41
|
+
*
|
|
42
|
+
* A macOS GUI app does NOT inherit the shell PATH, so the handler must use an
|
|
43
|
+
* absolute path. Prefer the `agents` shim on PATH (directly executable); fall
|
|
44
|
+
* back to `<node> <entry>` for a bare JS install.
|
|
45
|
+
*/
|
|
46
|
+
export function resolveAgentsInvocation(platform = os.platform()) {
|
|
47
|
+
const onPath = whichAgents(platform);
|
|
48
|
+
if (onPath)
|
|
49
|
+
return platform === 'win32' ? `"${onPath}"` : shQuote(onPath);
|
|
50
|
+
const entry = getAgentsBinPath();
|
|
51
|
+
if (platform === 'win32')
|
|
52
|
+
return `"${process.execPath}" "${entry}"`;
|
|
53
|
+
return `${shQuote(process.execPath)} ${shQuote(entry)}`;
|
|
54
|
+
}
|
|
55
|
+
function whichAgents(platform) {
|
|
56
|
+
try {
|
|
57
|
+
const cmd = platform === 'win32' ? 'where' : 'which';
|
|
58
|
+
const out = execFileSync(cmd, ['agents'], { encoding: 'utf8' }).trim();
|
|
59
|
+
const first = out.split(/\r?\n/)[0]?.trim();
|
|
60
|
+
return first && fs.existsSync(first) ? first : null;
|
|
61
|
+
}
|
|
62
|
+
catch {
|
|
63
|
+
return null;
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
// ---------------------------------------------------------------------------
|
|
67
|
+
// Pure content generators (unit-tested).
|
|
68
|
+
// ---------------------------------------------------------------------------
|
|
69
|
+
/** The freedesktop `.desktop` entry that claims `x-scheme-handler/agents`. */
|
|
70
|
+
export function linuxDesktopEntry(invocation) {
|
|
71
|
+
return [
|
|
72
|
+
'[Desktop Entry]',
|
|
73
|
+
'Type=Application',
|
|
74
|
+
'Name=Agents URL Handler',
|
|
75
|
+
'Comment=Resume an agents session from an agents:// deep link',
|
|
76
|
+
`Exec=${invocation} open %u`,
|
|
77
|
+
'Terminal=false',
|
|
78
|
+
'NoDisplay=true',
|
|
79
|
+
'MimeType=x-scheme-handler/agents;',
|
|
80
|
+
'',
|
|
81
|
+
].join('\n');
|
|
82
|
+
}
|
|
83
|
+
/**
|
|
84
|
+
* AppleScript whose `on open location` handler fires when macOS routes an
|
|
85
|
+
* `agents://` URL to the app. `quoted form of` makes the URL a single safe
|
|
86
|
+
* shell argument — the URL is never concatenated unquoted.
|
|
87
|
+
*/
|
|
88
|
+
export function macAppleScriptSource(invocation) {
|
|
89
|
+
// Escape the (already shell-quoted) invocation for an AppleScript double-quoted
|
|
90
|
+
// string literal, so a `"` or `\` in the install path cannot break osacompile.
|
|
91
|
+
const literal = invocation.replace(/\\/g, '\\\\').replace(/"/g, '\\"');
|
|
92
|
+
return [
|
|
93
|
+
'on open location this_URL',
|
|
94
|
+
`\tdo shell script "${literal} open " & quoted form of this_URL`,
|
|
95
|
+
'end open location',
|
|
96
|
+
].join('\n');
|
|
97
|
+
}
|
|
98
|
+
/** PlistBuddy commands that add the `agents` URL type to a compiled app's Info.plist. */
|
|
99
|
+
export function macPlistBuddyCommands(plistPath) {
|
|
100
|
+
const b = ['/usr/libexec/PlistBuddy', '-c'];
|
|
101
|
+
return [
|
|
102
|
+
[...b, 'Add :CFBundleIdentifier string ' + MAC_BUNDLE_ID, plistPath],
|
|
103
|
+
[...b, 'Add :CFBundleURLTypes array', plistPath],
|
|
104
|
+
[...b, 'Add :CFBundleURLTypes:0 dict', plistPath],
|
|
105
|
+
[...b, 'Add :CFBundleURLTypes:0:CFBundleURLName string ' + MAC_BUNDLE_ID, plistPath],
|
|
106
|
+
[...b, 'Add :CFBundleURLTypes:0:CFBundleURLSchemes array', plistPath],
|
|
107
|
+
[...b, `Add :CFBundleURLTypes:0:CFBundleURLSchemes:0 string ${AGENTS_URL_SCHEME}`, plistPath],
|
|
108
|
+
];
|
|
109
|
+
}
|
|
110
|
+
/** `reg add` argv lists that register the scheme under HKCU on Windows. */
|
|
111
|
+
export function windowsRegistryCommands(invocation) {
|
|
112
|
+
const base = 'HKCU\\Software\\Classes\\agents';
|
|
113
|
+
return [
|
|
114
|
+
['add', base, '/ve', '/d', 'URL:agents Protocol', '/f'],
|
|
115
|
+
['add', base, '/v', 'URL Protocol', '/d', '', '/f'],
|
|
116
|
+
['add', `${base}\\shell\\open\\command`, '/ve', '/d', `${invocation} open "%1"`, '/f'],
|
|
117
|
+
];
|
|
118
|
+
}
|
|
119
|
+
// ---------------------------------------------------------------------------
|
|
120
|
+
// Paths.
|
|
121
|
+
// ---------------------------------------------------------------------------
|
|
122
|
+
export function linuxDesktopPath(home = os.homedir()) {
|
|
123
|
+
return path.join(home, '.local', 'share', 'applications', LINUX_DESKTOP_FILE);
|
|
124
|
+
}
|
|
125
|
+
export function macAppPath(home = os.homedir()) {
|
|
126
|
+
return path.join(home, 'Applications', MAC_APP_NAME);
|
|
127
|
+
}
|
|
128
|
+
// ---------------------------------------------------------------------------
|
|
129
|
+
// Status.
|
|
130
|
+
// ---------------------------------------------------------------------------
|
|
131
|
+
/** Whether the handler artifact exists on disk (a cheap, side-effect-free check). */
|
|
132
|
+
export function agentsUrlSchemeStatus(platform = os.platform(), home = os.homedir()) {
|
|
133
|
+
if (platform === 'linux') {
|
|
134
|
+
const p = linuxDesktopPath(home);
|
|
135
|
+
return fs.existsSync(p)
|
|
136
|
+
? { registered: true, platform, detail: `handler: ${p}` }
|
|
137
|
+
: { registered: false, platform, detail: `no handler (${p}) — run: agents open register` };
|
|
138
|
+
}
|
|
139
|
+
if (platform === 'darwin') {
|
|
140
|
+
const p = macAppPath(home);
|
|
141
|
+
return fs.existsSync(p)
|
|
142
|
+
? { registered: true, platform, detail: `handler: ${p}` }
|
|
143
|
+
: { registered: false, platform, detail: `no handler (${p}) — run: agents open register` };
|
|
144
|
+
}
|
|
145
|
+
if (platform === 'win32') {
|
|
146
|
+
const ok = windowsSchemeRegistered();
|
|
147
|
+
return ok
|
|
148
|
+
? { registered: true, platform, detail: 'handler: HKCU\\Software\\Classes\\agents' }
|
|
149
|
+
: { registered: false, platform, detail: 'no handler — run: agents open register' };
|
|
150
|
+
}
|
|
151
|
+
return { registered: false, platform, detail: `unsupported platform: ${platform}` };
|
|
152
|
+
}
|
|
153
|
+
function windowsSchemeRegistered() {
|
|
154
|
+
try {
|
|
155
|
+
execFileSync('reg', ['query', 'HKCU\\Software\\Classes\\agents\\shell\\open\\command'], { stdio: 'ignore' });
|
|
156
|
+
return true;
|
|
157
|
+
}
|
|
158
|
+
catch {
|
|
159
|
+
return false;
|
|
160
|
+
}
|
|
161
|
+
}
|
|
162
|
+
export function registerAgentsUrlScheme(opts = {}) {
|
|
163
|
+
const platform = opts.platform ?? os.platform();
|
|
164
|
+
const home = opts.home ?? os.homedir();
|
|
165
|
+
if (opts.ifMissing && agentsUrlSchemeStatus(platform, home).registered) {
|
|
166
|
+
return agentsUrlSchemeStatus(platform, home);
|
|
167
|
+
}
|
|
168
|
+
try {
|
|
169
|
+
if (platform === 'linux')
|
|
170
|
+
return registerLinux(home);
|
|
171
|
+
if (platform === 'darwin')
|
|
172
|
+
return registerMac(home);
|
|
173
|
+
if (platform === 'win32')
|
|
174
|
+
return registerWindows(platform);
|
|
175
|
+
return { registered: false, platform, detail: `unsupported platform: ${platform}` };
|
|
176
|
+
}
|
|
177
|
+
catch (err) {
|
|
178
|
+
return { registered: false, platform, detail: `registration failed: ${err.message}` };
|
|
179
|
+
}
|
|
180
|
+
}
|
|
181
|
+
export function unregisterAgentsUrlScheme(opts = {}) {
|
|
182
|
+
const platform = opts.platform ?? os.platform();
|
|
183
|
+
const home = opts.home ?? os.homedir();
|
|
184
|
+
try {
|
|
185
|
+
if (platform === 'linux') {
|
|
186
|
+
fs.rmSync(linuxDesktopPath(home), { force: true });
|
|
187
|
+
run('update-desktop-database', [path.dirname(linuxDesktopPath(home))], true);
|
|
188
|
+
return { registered: false, platform, detail: 'handler removed' };
|
|
189
|
+
}
|
|
190
|
+
if (platform === 'darwin') {
|
|
191
|
+
fs.rmSync(macAppPath(home), { recursive: true, force: true });
|
|
192
|
+
return { registered: false, platform, detail: 'handler removed' };
|
|
193
|
+
}
|
|
194
|
+
if (platform === 'win32') {
|
|
195
|
+
run('reg', ['delete', 'HKCU\\Software\\Classes\\agents', '/f'], true);
|
|
196
|
+
return { registered: false, platform, detail: 'handler removed' };
|
|
197
|
+
}
|
|
198
|
+
return { registered: false, platform, detail: `unsupported platform: ${platform}` };
|
|
199
|
+
}
|
|
200
|
+
catch (err) {
|
|
201
|
+
return { registered: agentsUrlSchemeStatus(platform, home).registered, platform, detail: `removal failed: ${err.message}` };
|
|
202
|
+
}
|
|
203
|
+
}
|
|
204
|
+
function registerLinux(home) {
|
|
205
|
+
const invocation = resolveAgentsInvocation('linux');
|
|
206
|
+
const dest = linuxDesktopPath(home);
|
|
207
|
+
fs.mkdirSync(path.dirname(dest), { recursive: true });
|
|
208
|
+
fs.writeFileSync(dest, linuxDesktopEntry(invocation), 'utf8');
|
|
209
|
+
// Make it the default handler for the scheme; best-effort DB refresh.
|
|
210
|
+
run('xdg-mime', ['default', LINUX_DESKTOP_FILE, 'x-scheme-handler/agents'], true);
|
|
211
|
+
run('update-desktop-database', [path.dirname(dest)], true);
|
|
212
|
+
return { registered: true, platform: 'linux', detail: `handler: ${dest}` };
|
|
213
|
+
}
|
|
214
|
+
function registerMac(home) {
|
|
215
|
+
const invocation = resolveAgentsInvocation('darwin');
|
|
216
|
+
const app = macAppPath(home);
|
|
217
|
+
fs.mkdirSync(path.dirname(app), { recursive: true });
|
|
218
|
+
fs.rmSync(app, { recursive: true, force: true });
|
|
219
|
+
// Compile the AppleScript into an .app, then inject the URL scheme into its plist.
|
|
220
|
+
const scriptFile = path.join(os.tmpdir(), `agents-url-handler-${process.pid}.applescript`);
|
|
221
|
+
fs.writeFileSync(scriptFile, macAppleScriptSource(invocation), 'utf8');
|
|
222
|
+
try {
|
|
223
|
+
run('osacompile', ['-o', app, scriptFile], false);
|
|
224
|
+
}
|
|
225
|
+
finally {
|
|
226
|
+
fs.rmSync(scriptFile, { force: true });
|
|
227
|
+
}
|
|
228
|
+
const plist = path.join(app, 'Contents', 'Info.plist');
|
|
229
|
+
// Non-optional: if the URL type is not written, the scheme is never claimed —
|
|
230
|
+
// registerAgentsUrlScheme must report failure, not a false "registered".
|
|
231
|
+
for (const cmd of macPlistBuddyCommands(plist))
|
|
232
|
+
run(cmd[0], cmd.slice(1), false);
|
|
233
|
+
// Register with LaunchServices so the scheme resolves without a reboot.
|
|
234
|
+
const lsregister = '/System/Library/Frameworks/CoreServices.framework/Versions/A/Frameworks/LaunchServices.framework/Versions/A/Support/lsregister';
|
|
235
|
+
run(lsregister, ['-f', app], true);
|
|
236
|
+
return { registered: true, platform: 'darwin', detail: `handler: ${app}` };
|
|
237
|
+
}
|
|
238
|
+
function registerWindows(platform) {
|
|
239
|
+
const invocation = resolveAgentsInvocation('win32');
|
|
240
|
+
for (const args of windowsRegistryCommands(invocation))
|
|
241
|
+
run('reg', args, false);
|
|
242
|
+
return { registered: true, platform, detail: 'handler: HKCU\\Software\\Classes\\agents' };
|
|
243
|
+
}
|
|
244
|
+
/** Run a helper command. `optional` swallows failures (best-effort DB refreshes). */
|
|
245
|
+
function run(cmd, args, optional) {
|
|
246
|
+
try {
|
|
247
|
+
execFileSync(cmd, args, { stdio: 'ignore' });
|
|
248
|
+
}
|
|
249
|
+
catch (err) {
|
|
250
|
+
if (!optional)
|
|
251
|
+
throw err;
|
|
252
|
+
}
|
|
253
|
+
}
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Parse the `agents://` deep-link scheme.
|
|
3
|
+
*
|
|
4
|
+
* A rendered artifact (a plan or report) embeds `agents://session/<id>` in its
|
|
5
|
+
* provenance line. Clicking it hands the URL to the OS, which routes it to the
|
|
6
|
+
* registered handler (see register.ts) that runs `agents open <url>`. This module
|
|
7
|
+
* turns that URL into a validated {@link AgentsSessionLink} the resume dispatcher
|
|
8
|
+
* consumes.
|
|
9
|
+
*
|
|
10
|
+
* Parsing is deliberately strict: the session id is the only thing that ever
|
|
11
|
+
* reaches a child process, and the `open` command passes it as argv (never
|
|
12
|
+
* interpolated into a shell), so a hostile URL cannot inject a command. Anything
|
|
13
|
+
* that is not `agents://session/<valid-id>` is rejected with a reason.
|
|
14
|
+
*
|
|
15
|
+
* URL shape:
|
|
16
|
+
* agents://session/<id> — resume <id>, owner host resolved from the id
|
|
17
|
+
* agents://session/<id>?host=<name> — the same, with a routing hint
|
|
18
|
+
*/
|
|
19
|
+
export interface AgentsSessionLink {
|
|
20
|
+
kind: 'session';
|
|
21
|
+
/** The session id (or short-id/alias) to resume. */
|
|
22
|
+
id: string;
|
|
23
|
+
/** Optional owning-host hint; resume self-resolves the owner from the id regardless. */
|
|
24
|
+
host?: string;
|
|
25
|
+
}
|
|
26
|
+
export interface AgentsUrlError {
|
|
27
|
+
error: string;
|
|
28
|
+
}
|
|
29
|
+
export declare function isDeepLinkSessionId(raw: string): boolean;
|
|
30
|
+
/**
|
|
31
|
+
* Parse an `agents://…` URL into a {@link AgentsSessionLink}, or return an
|
|
32
|
+
* {@link AgentsUrlError} with a human reason. Never throws.
|
|
33
|
+
*/
|
|
34
|
+
export declare function parseAgentsUrl(input: string): AgentsSessionLink | AgentsUrlError;
|
|
@@ -0,0 +1,78 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Parse the `agents://` deep-link scheme.
|
|
3
|
+
*
|
|
4
|
+
* A rendered artifact (a plan or report) embeds `agents://session/<id>` in its
|
|
5
|
+
* provenance line. Clicking it hands the URL to the OS, which routes it to the
|
|
6
|
+
* registered handler (see register.ts) that runs `agents open <url>`. This module
|
|
7
|
+
* turns that URL into a validated {@link AgentsSessionLink} the resume dispatcher
|
|
8
|
+
* consumes.
|
|
9
|
+
*
|
|
10
|
+
* Parsing is deliberately strict: the session id is the only thing that ever
|
|
11
|
+
* reaches a child process, and the `open` command passes it as argv (never
|
|
12
|
+
* interpolated into a shell), so a hostile URL cannot inject a command. Anything
|
|
13
|
+
* that is not `agents://session/<valid-id>` is rejected with a reason.
|
|
14
|
+
*
|
|
15
|
+
* URL shape:
|
|
16
|
+
* agents://session/<id> — resume <id>, owner host resolved from the id
|
|
17
|
+
* agents://session/<id>?host=<name> — the same, with a routing hint
|
|
18
|
+
*/
|
|
19
|
+
/**
|
|
20
|
+
* Session-id shapes accepted from a deep link. Mirrors `looksLikeSessionId`
|
|
21
|
+
* (lib/session/discover.ts) WITHOUT importing the heavy session module, so the
|
|
22
|
+
* `open` command stays cold-start cheap: a bare hex short-id/prefix (>=6 chars),
|
|
23
|
+
* a UUID (optionally `session_`-prefixed), a `ses_<ulid>` (OpenCode), or an
|
|
24
|
+
* `ag-…-<8hex>` tmux alias. The upper length bound is a sanity cap, not a format
|
|
25
|
+
* rule.
|
|
26
|
+
*/
|
|
27
|
+
const HEX_ID = /^[0-9a-f-]{6,}$/i;
|
|
28
|
+
const SES_ULID = /^ses_[0-9a-hjkmnp-tv-z]{26}$/i;
|
|
29
|
+
import { AG_TMUX_NAME_RE as AG_ALIAS } from '../session/types.js';
|
|
30
|
+
const HOST_HINT = /^[a-z0-9][a-z0-9._-]{0,63}$/i;
|
|
31
|
+
export function isDeepLinkSessionId(raw) {
|
|
32
|
+
const id = (raw ?? '').trim();
|
|
33
|
+
if (!id || id.length > 128)
|
|
34
|
+
return false;
|
|
35
|
+
const bare = id.replace(/^session_/i, '');
|
|
36
|
+
return HEX_ID.test(bare) || SES_ULID.test(id) || AG_ALIAS.test(id);
|
|
37
|
+
}
|
|
38
|
+
/**
|
|
39
|
+
* Parse an `agents://…` URL into a {@link AgentsSessionLink}, or return an
|
|
40
|
+
* {@link AgentsUrlError} with a human reason. Never throws.
|
|
41
|
+
*/
|
|
42
|
+
export function parseAgentsUrl(input) {
|
|
43
|
+
const raw = (input ?? '').trim();
|
|
44
|
+
if (!raw)
|
|
45
|
+
return { error: 'empty URL' };
|
|
46
|
+
let url;
|
|
47
|
+
try {
|
|
48
|
+
url = new URL(raw);
|
|
49
|
+
}
|
|
50
|
+
catch {
|
|
51
|
+
return { error: `not a URL: ${truncate(raw)}` };
|
|
52
|
+
}
|
|
53
|
+
if (url.protocol !== 'agents:') {
|
|
54
|
+
return { error: `unsupported scheme: ${url.protocol}// (expected agents://)` };
|
|
55
|
+
}
|
|
56
|
+
// agents://session/<id> → hostname="session", pathname="/<id>". The authority
|
|
57
|
+
// is compared case-insensitively because some browsers normalize its casing.
|
|
58
|
+
const verb = url.hostname.toLowerCase();
|
|
59
|
+
if (verb !== 'session') {
|
|
60
|
+
return { error: `unknown agents:// target "${verb || '(none)'}" (expected agents://session/<id>)` };
|
|
61
|
+
}
|
|
62
|
+
let id;
|
|
63
|
+
try {
|
|
64
|
+
id = decodeURIComponent(url.pathname.replace(/^\/+/, '')).trim();
|
|
65
|
+
}
|
|
66
|
+
catch {
|
|
67
|
+
return { error: 'malformed session id encoding' };
|
|
68
|
+
}
|
|
69
|
+
if (!isDeepLinkSessionId(id)) {
|
|
70
|
+
return { error: `invalid session id: ${truncate(id) || '(none)'}` };
|
|
71
|
+
}
|
|
72
|
+
const hostParam = url.searchParams.get('host')?.trim();
|
|
73
|
+
const host = hostParam && HOST_HINT.test(hostParam) ? hostParam : undefined;
|
|
74
|
+
return host ? { kind: 'session', id, host } : { kind: 'session', id };
|
|
75
|
+
}
|
|
76
|
+
function truncate(s, max = 60) {
|
|
77
|
+
return s.length > max ? `${s.slice(0, max)}…` : s;
|
|
78
|
+
}
|
|
@@ -1,46 +1,84 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* Device/user config keys — typed read/write over the
|
|
2
|
+
* Device/user config keys — typed read/write over the central agents.yaml store.
|
|
3
3
|
*
|
|
4
4
|
* One registry (`CONFIG_KEYS`) maps each CLI dotted name to where it lives:
|
|
5
|
-
* - user scope
|
|
6
|
-
*
|
|
7
|
-
* - device scope
|
|
8
|
-
*
|
|
5
|
+
* - user scope → central `~/.agents/agents.yaml` under `config:` (syncs
|
|
6
|
+
* fleet-wide via `agents repo push/pull`)
|
|
7
|
+
* - device scope → split by `visibility`, which asks WHO READS IT:
|
|
8
|
+
* · `shared` → central `fleet.devices.<name>.config`, because a PEER
|
|
9
|
+
* reads it (the ssh keys and platform to dial the box,
|
|
10
|
+
* agents.max-concurrent for placement, auto-launch and
|
|
11
|
+
* notes for fleet views). Names and non-secret values only
|
|
12
|
+
* (a secrets-bundle NAME is fine; a credential never is).
|
|
13
|
+
* · `machine` → the owning box's own doc, never the shared file, because
|
|
14
|
+
* nothing off-box reads it (browser.profile,
|
|
15
|
+
* browser.remote-control, scheduler.enabled,
|
|
16
|
+
* daemon.enabled).
|
|
9
17
|
*
|
|
10
|
-
*
|
|
11
|
-
*
|
|
12
|
-
*
|
|
13
|
-
*
|
|
14
|
-
* target a peer (`--device`-style).
|
|
18
|
+
* That split exists because "central for everything" put 13 machines on one
|
|
19
|
+
* tracked path and they stopped being able to pull. `browser.remote-control` is
|
|
20
|
+
* also a consent flag — syncing one box's opt-in to the rest was a security bug,
|
|
21
|
+
* not just churn.
|
|
15
22
|
*
|
|
16
|
-
*
|
|
17
|
-
*
|
|
18
|
-
*
|
|
23
|
+
* The device registry (`~/.agents/.history/devices/registry.json`) stays the
|
|
24
|
+
* DISCOVERY cache (address, tailscale snapshot, reachability); the profile
|
|
25
|
+
* fields config can override (ssh.*, platform, user) are overlaid onto it at
|
|
26
|
+
* read time by `lib/devices/resolve-profile.ts`.
|
|
19
27
|
*
|
|
20
|
-
*
|
|
28
|
+
* Legacy stores (per-device `devices/<host>/agents.yaml` config and
|
|
29
|
+
* `.history/devices/auto-launch.json`) are folded into the central block once
|
|
30
|
+
* by `lib/devices/config-migration.ts`, invoked on the first read/write in a
|
|
31
|
+
* process — after migration there is ONE read path, no fallback branches.
|
|
32
|
+
*
|
|
33
|
+
* Unset always means today's behavior (the documented default).
|
|
21
34
|
*/
|
|
22
35
|
/** Which tier of the agents.yaml store a key lives in. */
|
|
23
36
|
export type ConfigScope = 'user' | 'device';
|
|
37
|
+
/**
|
|
38
|
+
* For a device-scope key: WHO READS IT, which is what decides where it is stored.
|
|
39
|
+
*
|
|
40
|
+
* - `shared` — a PEER reads it, so it must be visible fleet-wide and lives in the
|
|
41
|
+
* tracked `fleet.devices.<name>.config`. `ssh.*` and `platform` are the
|
|
42
|
+
* load-bearing cases: machine A resolves them to build the ssh target for B
|
|
43
|
+
* (`lib/devices/resolve-profile.ts`), so it cannot ask B for them.
|
|
44
|
+
* - `machine` — only the owning box ever reads it, so it belongs in that box's
|
|
45
|
+
* own gitignored doc and must never reach the fleet-shared file. Storing these
|
|
46
|
+
* centrally is what makes 13 machines write one tracked path.
|
|
47
|
+
*
|
|
48
|
+
* Declaring this is MANDATORY for a device-scope key — the union below makes
|
|
49
|
+
* omitting it a compile error, mirroring how `META_KEY_SCOPE` (lib/state.ts) uses
|
|
50
|
+
* an exhaustive `Record<keyof Meta, ...>`. Before this, a new key picked its home
|
|
51
|
+
* by hand with no signal, which is how operator config drifted into the shared
|
|
52
|
+
* file twice.
|
|
53
|
+
*/
|
|
54
|
+
export type ConfigVisibility = 'shared' | 'machine';
|
|
24
55
|
/** Value type of a config key — drives validation and `--json` rendering. */
|
|
25
56
|
export type ConfigType = 'string' | 'int' | 'bool' | 'string-list';
|
|
26
|
-
/**
|
|
27
|
-
|
|
57
|
+
/** Fields every key carries, regardless of scope. */
|
|
58
|
+
interface ConfigKeySpecBase {
|
|
28
59
|
/** CLI dotted name, e.g. `interactive.host`. */
|
|
29
60
|
name: string;
|
|
30
|
-
/** camelCase key under the YAML
|
|
61
|
+
/** camelCase key under the YAML config block. */
|
|
31
62
|
yamlKey: string;
|
|
32
|
-
scope: ConfigScope;
|
|
33
63
|
type: ConfigType;
|
|
34
64
|
/** One-line description for help/list output. */
|
|
35
65
|
description: string;
|
|
36
|
-
/**
|
|
37
|
-
|
|
38
|
-
* `config:` block (only `browser.profile` → `defaultBrowserProfile` today).
|
|
39
|
-
*/
|
|
40
|
-
field?: 'defaultBrowserProfile';
|
|
66
|
+
/** The effective value when the key is unset (bool keys; drives the interactive menu's default). */
|
|
67
|
+
defaultValue?: unknown;
|
|
41
68
|
/** Extra validation beyond the type check; return an error string or null. */
|
|
42
69
|
validate?: (value: unknown) => string | null;
|
|
43
70
|
}
|
|
71
|
+
/**
|
|
72
|
+
* One known config key. A device-scope key MUST declare its `visibility`; a
|
|
73
|
+
* user-scope key has none (it is fleet-wide by definition).
|
|
74
|
+
*/
|
|
75
|
+
export type ConfigKeySpec = (ConfigKeySpecBase & {
|
|
76
|
+
scope: 'user';
|
|
77
|
+
visibility?: never;
|
|
78
|
+
}) | (ConfigKeySpecBase & {
|
|
79
|
+
scope: 'device';
|
|
80
|
+
visibility: ConfigVisibility;
|
|
81
|
+
});
|
|
44
82
|
/** A key with its resolved value and the layer that set it. */
|
|
45
83
|
export interface ConfigEntry {
|
|
46
84
|
spec: ConfigKeySpec;
|
|
@@ -49,22 +87,78 @@ export interface ConfigEntry {
|
|
|
49
87
|
/** Which layer set it; undefined when unset. */
|
|
50
88
|
layer?: ConfigScope;
|
|
51
89
|
}
|
|
52
|
-
/** Options scoping a read/write to a specific device
|
|
90
|
+
/** Options scoping a read/write to a specific device (default: this machine). */
|
|
53
91
|
export interface ConfigTarget {
|
|
54
92
|
device?: string;
|
|
55
93
|
}
|
|
56
94
|
export declare const CONFIG_KEYS: readonly ConfigKeySpec[];
|
|
57
95
|
/** Look up a key spec by CLI dotted name, or throw listing the known keys. */
|
|
58
96
|
export declare function configKeySpec(name: string): ConfigKeySpec;
|
|
97
|
+
/**
|
|
98
|
+
* Fold the legacy per-device config stores into the central block, once per
|
|
99
|
+
* process. A failure is loud but non-fatal — config reads must keep working,
|
|
100
|
+
* and the next process retries the fold. Honors AGENTS_SKIP_MIGRATION=1, the
|
|
101
|
+
* same gate bootstrap's runMigration uses (tests pin it so a fork never folds
|
|
102
|
+
* the developer's real ~/.agents as a side effect).
|
|
103
|
+
*
|
|
104
|
+
* Call this ONLY from a lifecycle entry point (daemon boot, `runMigration`).
|
|
105
|
+
* It must never hang off a config read or write: `~/.agents/agents.yaml` is a
|
|
106
|
+
* tracked file shared by every machine in the fleet, so a migration on the read
|
|
107
|
+
* path means an ordinary `agents config get` can dirty the shared file. That is
|
|
108
|
+
* what left yosemite-s0 unable to pull — 13 machines each rewriting one tracked
|
|
109
|
+
* path, on nearly every command.
|
|
110
|
+
*/
|
|
111
|
+
export declare function ensureDeviceConfigMigrated(): void;
|
|
112
|
+
/**
|
|
113
|
+
* The raw device-scope config block for `device` from the central
|
|
114
|
+
* `fleet.devices.<name>.config` map ({} when unset). This is the single read
|
|
115
|
+
* path post-migration — the profile resolver (`lib/devices/resolve-profile.ts`)
|
|
116
|
+
* goes through here. Deliberately does NOT auto-trigger the migration: it
|
|
117
|
+
* serves the hot dial/render paths, and the keys it resolves (ssh.*, platform)
|
|
118
|
+
* are new — they never existed in the legacy stores. Keys with legacy data are
|
|
119
|
+
* read through the public API below, which triggers the fold.
|
|
120
|
+
*/
|
|
121
|
+
export declare function readDeviceConfigValues(device: string): Record<string, unknown>;
|
|
59
122
|
/** Get one config key's value and the layer that set it. */
|
|
60
123
|
export declare function getConfigValue(name: string, opts?: ConfigTarget): ConfigEntry;
|
|
61
|
-
/**
|
|
124
|
+
/**
|
|
125
|
+
* List every known key with its value and the layer that set it.
|
|
126
|
+
*
|
|
127
|
+
* Listing a PEER omits its machine-local keys rather than throwing. Their values
|
|
128
|
+
* live in that box's own doc and are genuinely unknowable from here, but a bulk
|
|
129
|
+
* listing must not hard-fail because one key in the registry is unreadable —
|
|
130
|
+
* `agents devices config <peer>` should still show everything it CAN resolve.
|
|
131
|
+
* Asking for such a key by name still errors, with the `agents ssh` fix named.
|
|
132
|
+
*/
|
|
62
133
|
export declare function listConfig(opts?: ConfigTarget): ConfigEntry[];
|
|
134
|
+
/** List user-scope config keys with their values. Used to show inherited settings
|
|
135
|
+
* in per-device views without implying those keys are device-local. */
|
|
136
|
+
export declare function listUserConfig(): ConfigEntry[];
|
|
137
|
+
/** Resolve the explicit usage host, falling back to the user's interactive host. */
|
|
138
|
+
export declare function resolveUsagePrimaryHost(): string | null;
|
|
63
139
|
/** Set a config key (validated). Device-scope keys target this machine unless `opts.device` names a peer. */
|
|
64
140
|
export declare function setConfigValue(name: string, value: unknown, opts?: ConfigTarget): void;
|
|
65
141
|
/** Unset a config key — restores default behavior. No-op when already unset. */
|
|
66
142
|
export declare function unsetConfigValue(name: string, opts?: ConfigTarget): void;
|
|
67
|
-
/**
|
|
143
|
+
/** A device's auto-launch flags, as read by the ext's launch ranking. */
|
|
144
|
+
export interface AutoLaunchPreference {
|
|
145
|
+
enabled?: boolean;
|
|
146
|
+
preferred?: boolean;
|
|
147
|
+
}
|
|
148
|
+
/** True if the device is enabled for auto-launch. Unset defaults to true. */
|
|
149
|
+
export declare function isAutoLaunchEnabled(name: string): boolean;
|
|
150
|
+
/** Set whether a device is enabled for auto-launch. Setting the default
|
|
151
|
+
* (enabled) removes the key to keep the block minimal. */
|
|
152
|
+
export declare function setAutoLaunchEnabled(name: string, enabled: boolean): void;
|
|
153
|
+
/** True if the device is preferred for auto-launch ranking. */
|
|
154
|
+
export declare function isAutoLaunchPreferred(name: string): boolean;
|
|
155
|
+
/** Set whether a device is preferred for auto-launch. Setting the default
|
|
156
|
+
* (not preferred) removes the key to keep the block minimal. */
|
|
157
|
+
export declare function setAutoLaunchPreferred(name: string, preferred: boolean): void;
|
|
158
|
+
/** Every device's auto-launch flags, keyed by device name (set flags only) —
|
|
159
|
+
* the shape the ext's launch ranking consumes. */
|
|
160
|
+
export declare function loadAutoLaunchPreferences(): Record<string, AutoLaunchPreference>;
|
|
161
|
+
/** True unless this machine's config disables the routines scheduler. */
|
|
68
162
|
export declare function isSchedulerEnabled(): boolean;
|
|
69
163
|
/**
|
|
70
164
|
* Throw when the routines scheduler is disabled on this machine, naming the
|
|
@@ -73,7 +167,7 @@ export declare function isSchedulerEnabled(): boolean;
|
|
|
73
167
|
* scheduler init) refuses with.
|
|
74
168
|
*/
|
|
75
169
|
export declare function assertSchedulerEnabled(): void;
|
|
76
|
-
/** True unless this machine's
|
|
170
|
+
/** True unless this machine's config disables the daemon outright (top-level kill switch). */
|
|
77
171
|
export declare function isDaemonEnabled(): boolean;
|
|
78
172
|
/**
|
|
79
173
|
* Throw when the daemon is disabled on this machine, naming the setting and
|
|
@@ -84,9 +178,10 @@ export declare function isDaemonEnabled(): boolean;
|
|
|
84
178
|
*/
|
|
85
179
|
export declare function assertDaemonEnabled(): void;
|
|
86
180
|
/**
|
|
87
|
-
* Read the `agents.max-concurrent` cap for each named device from
|
|
88
|
-
*
|
|
181
|
+
* Read the `agents.max-concurrent` cap for each named device from the central
|
|
182
|
+
* config block (no SSH). Devices without a cap are omitted — uncapped is the
|
|
89
183
|
* default. Used as an input to host ranking (teams placement, Factory
|
|
90
184
|
* auto-launch), never as a remote probe.
|
|
91
185
|
*/
|
|
92
186
|
export declare function readMaxConcurrentCaps(devices: string[]): Record<string, number>;
|
|
187
|
+
export {};
|