@phnx-labs/agents-cli 1.22.35 → 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.
Files changed (487) hide show
  1. package/CHANGELOG.md +666 -2
  2. package/README.md +75 -35
  3. package/dist/bin/agents +0 -0
  4. package/dist/bootstrap.d.ts +15 -0
  5. package/dist/bootstrap.js +1211 -0
  6. package/dist/commands/accounts.d.ts +4 -11
  7. package/dist/commands/accounts.js +159 -27
  8. package/dist/commands/attach.js +17 -4
  9. package/dist/commands/audit.d.ts +8 -8
  10. package/dist/commands/audit.js +57 -47
  11. package/dist/commands/browser.js +15 -11
  12. package/dist/commands/cloud.js +1 -1
  13. package/dist/commands/commands.js +0 -11
  14. package/dist/commands/computer-actions.js +33 -0
  15. package/dist/commands/computer-sessions-picker.d.ts +21 -0
  16. package/dist/commands/computer-sessions-picker.js +141 -0
  17. package/dist/commands/computer.d.ts +16 -0
  18. package/dist/commands/computer.js +37 -0
  19. package/dist/commands/config.d.ts +17 -0
  20. package/dist/commands/config.js +401 -0
  21. package/dist/commands/cp.d.ts +84 -0
  22. package/dist/commands/cp.js +231 -0
  23. package/dist/commands/daemon.js +243 -14
  24. package/dist/commands/detach-core.d.ts +1 -1
  25. package/dist/commands/detach-core.js +12 -2
  26. package/dist/commands/detach.js +1 -1
  27. package/dist/commands/doctor.js +64 -5
  28. package/dist/commands/events.d.ts +24 -12
  29. package/dist/commands/events.js +144 -28
  30. package/dist/commands/exec.js +85 -41
  31. package/dist/commands/feed.d.ts +1 -1
  32. package/dist/commands/feed.js +16 -8
  33. package/dist/commands/focus.d.ts +33 -1
  34. package/dist/commands/focus.js +177 -17
  35. package/dist/commands/funnel.d.ts +1 -1
  36. package/dist/commands/go.js +9 -8
  37. package/dist/commands/harness-wizard.d.ts +1 -0
  38. package/dist/commands/harness-wizard.js +18 -20
  39. package/dist/commands/harness.d.ts +2 -0
  40. package/dist/commands/harness.js +59 -26
  41. package/dist/commands/hooks.js +0 -11
  42. package/dist/commands/inspect.d.ts +94 -1
  43. package/dist/commands/inspect.js +866 -40
  44. package/dist/commands/lease.d.ts +4 -4
  45. package/dist/commands/lease.js +6 -6
  46. package/dist/commands/login.js +0 -13
  47. package/dist/commands/logs.d.ts +2 -2
  48. package/dist/commands/logs.js +2 -2
  49. package/dist/commands/mcp.js +7 -2
  50. package/dist/commands/memory.js +7 -2
  51. package/dist/commands/message.d.ts +1 -1
  52. package/dist/commands/message.js +37 -6
  53. package/dist/commands/models.js +4 -0
  54. package/dist/commands/monitors.d.ts +0 -1
  55. package/dist/commands/monitors.js +199 -16
  56. package/dist/commands/open.d.ts +18 -0
  57. package/dist/commands/open.js +57 -0
  58. package/dist/commands/packages.js +2 -107
  59. package/dist/commands/plugins.js +6 -3
  60. package/dist/commands/profiles.d.ts +1 -0
  61. package/dist/commands/profiles.js +16 -160
  62. package/dist/commands/projects.d.ts +28 -0
  63. package/dist/commands/projects.js +125 -5
  64. package/dist/commands/reconnect.js +9 -3
  65. package/dist/commands/repo.js +42 -1
  66. package/dist/commands/resource-view.d.ts +17 -0
  67. package/dist/commands/resource-view.js +36 -14
  68. package/dist/commands/resume.js +9 -2
  69. package/dist/commands/routines.d.ts +0 -2
  70. package/dist/commands/routines.js +473 -289
  71. package/dist/commands/secrets.js +52 -9
  72. package/dist/commands/sessions-export.d.ts +47 -0
  73. package/dist/commands/sessions-export.js +116 -6
  74. package/dist/commands/sessions-import.d.ts +17 -0
  75. package/dist/commands/sessions-import.js +114 -6
  76. package/dist/commands/sessions-migrate.d.ts +27 -0
  77. package/dist/commands/sessions-migrate.js +50 -9
  78. package/dist/commands/sessions-picker.js +23 -4
  79. package/dist/commands/sessions-resume.d.ts +5 -3
  80. package/dist/commands/sessions-resume.js +30 -8
  81. package/dist/commands/sessions-watch.d.ts +2 -0
  82. package/dist/commands/sessions-watch.js +53 -0
  83. package/dist/commands/sessions.d.ts +66 -3
  84. package/dist/commands/sessions.js +298 -47
  85. package/dist/commands/set.d.ts +1 -1
  86. package/dist/commands/set.js +2 -2
  87. package/dist/commands/setup-browser.js +2 -2
  88. package/dist/commands/setup-mine.js +0 -1
  89. package/dist/commands/setup-preferences.js +1 -1
  90. package/dist/commands/setup-share.js +34 -4
  91. package/dist/commands/setup.d.ts +5 -0
  92. package/dist/commands/setup.js +26 -0
  93. package/dist/commands/share.d.ts +67 -0
  94. package/dist/commands/share.js +275 -12
  95. package/dist/commands/skills.js +0 -11
  96. package/dist/commands/snapshot.js +1 -1
  97. package/dist/commands/ssh.d.ts +18 -0
  98. package/dist/commands/ssh.js +549 -210
  99. package/dist/commands/sync.d.ts +5 -0
  100. package/dist/commands/sync.js +212 -32
  101. package/dist/commands/teams.d.ts +13 -0
  102. package/dist/commands/teams.js +187 -30
  103. package/dist/commands/tickets.d.ts +2 -0
  104. package/dist/commands/tickets.js +43 -0
  105. package/dist/commands/update.js +2 -4
  106. package/dist/commands/usage.js +5 -3
  107. package/dist/commands/versions.js +11 -5
  108. package/dist/commands/view.js +15 -7
  109. package/dist/commands/webhook.d.ts +2 -2
  110. package/dist/commands/webhook.js +7 -7
  111. package/dist/index.d.ts +18 -2
  112. package/dist/index.js +53 -1264
  113. package/dist/lib/account-catalog.d.ts +18 -0
  114. package/dist/lib/account-catalog.js +38 -0
  115. package/dist/lib/account-provider-registry.d.ts +18 -0
  116. package/dist/lib/account-provider-registry.js +59 -0
  117. package/dist/lib/account-registry.d.ts +40 -0
  118. package/dist/lib/account-registry.js +239 -0
  119. package/dist/lib/account-schema.d.ts +44 -0
  120. package/dist/lib/account-schema.js +91 -0
  121. package/dist/lib/account-state-service.d.ts +21 -0
  122. package/dist/lib/account-state-service.js +60 -0
  123. package/dist/lib/activity.d.ts +1 -1
  124. package/dist/lib/activity.js +8 -1
  125. package/dist/lib/add-dir.d.ts +80 -0
  126. package/dist/lib/add-dir.js +241 -0
  127. package/dist/lib/agent-cli-commands.d.ts +11 -0
  128. package/dist/lib/agent-cli-commands.js +30 -0
  129. package/dist/lib/agents.js +44 -36
  130. package/dist/lib/answer-router.js +1 -1
  131. package/dist/lib/audit/log.d.ts +10 -27
  132. package/dist/lib/audit/log.js +20 -33
  133. package/dist/lib/auth-health.d.ts +9 -2
  134. package/dist/lib/auth-health.js +42 -9
  135. package/dist/lib/auto-pull-worker.js +7 -3
  136. package/dist/lib/auto-pull.d.ts +44 -3
  137. package/dist/lib/auto-pull.js +88 -5
  138. package/dist/lib/binary-shadow.d.ts +28 -0
  139. package/dist/lib/binary-shadow.js +121 -0
  140. package/dist/lib/brand.js +9 -3
  141. package/dist/lib/browser/ipc.d.ts +30 -0
  142. package/dist/lib/browser/ipc.js +81 -4
  143. package/dist/lib/browser/profiles.d.ts +3 -2
  144. package/dist/lib/browser/profiles.js +65 -22
  145. package/dist/lib/browser/service.d.ts +4 -0
  146. package/dist/lib/browser/service.js +30 -3
  147. package/dist/lib/browser/sessions-list.d.ts +22 -2
  148. package/dist/lib/browser/sessions-list.js +54 -6
  149. package/dist/lib/browser/stream.d.ts +2 -0
  150. package/dist/lib/browser/stream.js +1 -0
  151. package/dist/lib/browser/types.d.ts +19 -0
  152. package/dist/lib/byok-usage.d.ts +9 -2
  153. package/dist/lib/byok-usage.js +133 -31
  154. package/dist/lib/cli-entry.d.ts +11 -0
  155. package/dist/lib/cli-entry.js +46 -0
  156. package/dist/lib/cloud/host.d.ts +1 -1
  157. package/dist/lib/cloud/host.js +2 -2
  158. package/dist/lib/cloud/registry.js +1 -1
  159. package/dist/lib/cloud/types.d.ts +1 -1
  160. package/dist/lib/commands.d.ts +2 -0
  161. package/dist/lib/commands.js +2 -0
  162. package/dist/lib/computer/sessions-list.d.ts +150 -0
  163. package/dist/lib/computer/sessions-list.js +363 -0
  164. package/dist/lib/config-keys.d.ts +86 -0
  165. package/dist/lib/config-keys.js +193 -0
  166. package/dist/lib/config-machine-keys.d.ts +12 -0
  167. package/dist/lib/config-machine-keys.js +17 -0
  168. package/dist/lib/config-transfer.js +3 -4
  169. package/dist/lib/crabbox/cli.d.ts +2 -2
  170. package/dist/lib/crabbox/cli.js +3 -3
  171. package/dist/lib/daemon-health.d.ts +22 -0
  172. package/dist/lib/daemon-health.js +33 -3
  173. package/dist/lib/daemon-services.d.ts +50 -0
  174. package/dist/lib/daemon-services.js +147 -0
  175. package/dist/lib/daemon-ticks.d.ts +35 -66
  176. package/dist/lib/daemon-ticks.js +77 -159
  177. package/dist/lib/daemon.d.ts +72 -4
  178. package/dist/lib/daemon.js +792 -202
  179. package/dist/lib/deeplink/register.d.ts +49 -0
  180. package/dist/lib/deeplink/register.js +253 -0
  181. package/dist/lib/deeplink/url.d.ts +34 -0
  182. package/dist/lib/deeplink/url.js +78 -0
  183. package/dist/lib/device-config.d.ts +124 -29
  184. package/dist/lib/device-config.js +346 -141
  185. package/dist/lib/devices/config-migration.d.ts +42 -0
  186. package/dist/lib/devices/config-migration.js +203 -0
  187. package/dist/lib/devices/connect.js +14 -7
  188. package/dist/lib/devices/doctor-findings.d.ts +4 -1
  189. package/dist/lib/devices/doctor-findings.js +20 -1
  190. package/dist/lib/devices/harness-inventory.d.ts +11 -2
  191. package/dist/lib/devices/harness-inventory.js +0 -0
  192. package/dist/lib/devices/health.d.ts +1 -1
  193. package/dist/lib/devices/health.js +1 -1
  194. package/dist/lib/devices/pending.d.ts +22 -1
  195. package/dist/lib/devices/pending.js +67 -2
  196. package/dist/lib/devices/registry.d.ts +0 -25
  197. package/dist/lib/devices/registry.js +2 -83
  198. package/dist/lib/devices/resolve-profile.d.ts +20 -0
  199. package/dist/lib/devices/resolve-profile.js +44 -0
  200. package/dist/lib/devices/rollout-verify.d.ts +101 -0
  201. package/dist/lib/devices/rollout-verify.js +193 -0
  202. package/dist/lib/devices/ssh-config.js +10 -6
  203. package/dist/lib/event-families.d.ts +28 -0
  204. package/dist/lib/event-families.js +159 -0
  205. package/dist/lib/event-stream.d.ts +9 -1
  206. package/dist/lib/event-stream.js +26 -9
  207. package/dist/lib/events.d.ts +9 -1
  208. package/dist/lib/events.js +21 -6
  209. package/dist/lib/exec.d.ts +30 -0
  210. package/dist/lib/exec.js +219 -121
  211. package/dist/lib/feed-broadcast.d.ts +25 -0
  212. package/dist/lib/feed-broadcast.js +33 -0
  213. package/dist/lib/feed.d.ts +1 -1
  214. package/dist/lib/feed.js +12 -2
  215. package/dist/lib/fleet/capture.js +15 -0
  216. package/dist/lib/fleet/manifest.js +9 -0
  217. package/dist/lib/fleet/types.d.ts +9 -0
  218. package/dist/lib/fleet-status.js +10 -8
  219. package/dist/lib/git.d.ts +20 -6
  220. package/dist/lib/git.js +121 -17
  221. package/dist/lib/hosts/dispatch.d.ts +8 -3
  222. package/dist/lib/hosts/dispatch.js +29 -3
  223. package/dist/lib/hosts/logs.d.ts +2 -2
  224. package/dist/lib/hosts/logs.js +2 -2
  225. package/dist/lib/hosts/option.js +1 -1
  226. package/dist/lib/hosts/passthrough.d.ts +2 -3
  227. package/dist/lib/hosts/passthrough.js +10 -24
  228. package/dist/lib/hosts/progress.js +2 -2
  229. package/dist/lib/hosts/providers/devices.d.ts +3 -3
  230. package/dist/lib/hosts/providers/devices.js +18 -12
  231. package/dist/lib/hosts/ready.d.ts +5 -1
  232. package/dist/lib/hosts/ready.js +9 -3
  233. package/dist/lib/hosts/reconcile.d.ts +2 -2
  234. package/dist/lib/hosts/reconcile.js +2 -2
  235. package/dist/lib/hosts/registry.js +14 -9
  236. package/dist/lib/hosts/remote-cmd.js +1 -1
  237. package/dist/lib/hosts/remote-os.d.ts +9 -6
  238. package/dist/lib/hosts/remote-os.js +13 -6
  239. package/dist/lib/hosts/routing-flag.d.ts +23 -0
  240. package/dist/lib/hosts/routing-flag.js +41 -0
  241. package/dist/lib/hosts/run-target.js +1 -1
  242. package/dist/lib/hosts/session-index.js +1 -1
  243. package/dist/lib/hosts/tasks.d.ts +6 -6
  244. package/dist/lib/hosts/tasks.js +4 -4
  245. package/dist/lib/hosts/types.js +1 -2
  246. package/dist/lib/installations/resolve.js +2 -8
  247. package/dist/lib/isolation-boundary-report.js +0 -1
  248. package/dist/lib/linear-cache.d.ts +7 -0
  249. package/dist/lib/linear-cache.js +31 -4
  250. package/dist/lib/linear-project-counts.d.ts +1 -1
  251. package/dist/lib/linear-project-counts.js +2 -3
  252. package/dist/lib/linear-projects.js +1 -1
  253. package/dist/lib/loop.d.ts +2 -2
  254. package/dist/lib/loop.js +1 -1
  255. package/dist/lib/mailbox-target.d.ts +1 -1
  256. package/dist/lib/mailbox-target.js +1 -1
  257. package/dist/lib/manifest.js +7 -4
  258. package/dist/lib/menubar/MenubarHelper.app/Contents/CodeResources +0 -0
  259. package/dist/lib/menubar/MenubarHelper.app/Contents/MacOS/MenubarHelper +0 -0
  260. package/dist/lib/menubar/snapshot.d.ts +3 -2
  261. package/dist/lib/menubar/snapshot.js +6 -2
  262. package/dist/lib/migrate-fold.d.ts +33 -0
  263. package/dist/lib/migrate-fold.js +130 -0
  264. package/dist/lib/migrate.d.ts +34 -34
  265. package/dist/lib/migrate.js +106 -128
  266. package/dist/lib/model-tier-overrides.d.ts +1 -1
  267. package/dist/lib/model-tier-overrides.js +15 -2
  268. package/dist/lib/monitors/config.d.ts +17 -3
  269. package/dist/lib/monitors/config.js +52 -18
  270. package/dist/lib/monitors/engine.d.ts +32 -1
  271. package/dist/lib/monitors/engine.js +94 -11
  272. package/dist/lib/monitors/fingerprint.d.ts +46 -0
  273. package/dist/lib/monitors/fingerprint.js +100 -0
  274. package/dist/lib/monitors/remote.d.ts +47 -0
  275. package/dist/lib/monitors/remote.js +81 -0
  276. package/dist/lib/monitors/state.d.ts +39 -0
  277. package/dist/lib/monitors/state.js +56 -0
  278. package/dist/lib/onepassword.d.ts +17 -0
  279. package/dist/lib/onepassword.js +52 -22
  280. package/dist/lib/open-url.js +1 -1
  281. package/dist/lib/picker.d.ts +14 -2
  282. package/dist/lib/picker.js +35 -13
  283. package/dist/lib/placement.d.ts +1 -1
  284. package/dist/lib/placement.js +1 -1
  285. package/dist/lib/pr-land-detach.d.ts +32 -0
  286. package/dist/lib/pr-land-detach.js +79 -0
  287. package/dist/lib/profiles-presets.js +13 -0
  288. package/dist/lib/profiles.d.ts +2 -0
  289. package/dist/lib/profiles.js +44 -1
  290. package/dist/lib/project-focus.d.ts +1 -1
  291. package/dist/lib/project-focus.js +1 -1
  292. package/dist/lib/project-probe.d.ts +4 -1
  293. package/dist/lib/project-probe.js +5 -4
  294. package/dist/lib/project-resources.js +2 -18
  295. package/dist/lib/project-root.d.ts +16 -0
  296. package/dist/lib/project-root.js +20 -2
  297. package/dist/lib/projects.d.ts +20 -1
  298. package/dist/lib/projects.js +78 -1
  299. package/dist/lib/refresh-coordinator.d.ts +24 -0
  300. package/dist/lib/refresh-coordinator.js +52 -0
  301. package/dist/lib/registry.d.ts +2 -2
  302. package/dist/lib/registry.js +1 -1
  303. package/dist/lib/resource-aliases.d.ts +13 -0
  304. package/dist/lib/resource-aliases.js +26 -0
  305. package/dist/lib/resources/types.d.ts +1 -1
  306. package/dist/lib/resources.d.ts +16 -0
  307. package/dist/lib/resources.js +66 -10
  308. package/dist/lib/rotate.d.ts +3 -4
  309. package/dist/lib/rotate.js +4 -5
  310. package/dist/lib/routine-activation.d.ts +22 -2
  311. package/dist/lib/routine-activation.js +63 -16
  312. package/dist/lib/routine-context.d.ts +9 -2
  313. package/dist/lib/routine-context.js +21 -6
  314. package/dist/lib/routines-project.d.ts +58 -48
  315. package/dist/lib/routines-project.js +190 -159
  316. package/dist/lib/routines.d.ts +41 -6
  317. package/dist/lib/routines.js +92 -34
  318. package/dist/lib/run-defaults.d.ts +5 -0
  319. package/dist/lib/run-defaults.js +11 -1
  320. package/dist/lib/runner.d.ts +10 -8
  321. package/dist/lib/runner.js +122 -39
  322. package/dist/lib/secrets/Agents CLI.app/Contents/CodeResources +0 -0
  323. package/dist/lib/secrets/Agents CLI.app/Contents/MacOS/Agents CLI +0 -0
  324. package/dist/lib/secrets/agent.d.ts +10 -3
  325. package/dist/lib/secrets/agent.js +43 -8
  326. package/dist/lib/secrets/bundles.d.ts +1 -0
  327. package/dist/lib/secrets/bundles.js +92 -80
  328. package/dist/lib/secrets/index.js +32 -9
  329. package/dist/lib/secrets/install-helper.d.ts +4 -4
  330. package/dist/lib/secrets/install-helper.js +4 -4
  331. package/dist/lib/secrets/push.d.ts +40 -6
  332. package/dist/lib/secrets/push.js +58 -11
  333. package/dist/lib/secrets/read-backoff.d.ts +1 -1
  334. package/dist/lib/secrets/read-backoff.js +1 -1
  335. package/dist/lib/secrets/remote.d.ts +24 -0
  336. package/dist/lib/secrets/remote.js +54 -4
  337. package/dist/lib/self-update.d.ts +108 -0
  338. package/dist/lib/self-update.js +276 -1
  339. package/dist/lib/session/active.d.ts +89 -5
  340. package/dist/lib/session/active.js +165 -10
  341. package/dist/lib/session/actor-sidecar.d.ts +1 -1
  342. package/dist/lib/session/actor-sidecar.js +2 -1
  343. package/dist/lib/session/db.d.ts +176 -2
  344. package/dist/lib/session/db.js +484 -17
  345. package/dist/lib/session/discover.js +27 -4
  346. package/dist/lib/session/hook-sessions.js +2 -2
  347. package/dist/lib/session/host-link.d.ts +2 -2
  348. package/dist/lib/session/host-link.js +2 -2
  349. package/dist/lib/session/pid-registry.d.ts +21 -0
  350. package/dist/lib/session/pid-registry.js +57 -0
  351. package/dist/lib/session/remote-active.js +15 -1
  352. package/dist/lib/session/remote.js +2 -2
  353. package/dist/lib/session/session-cache.d.ts +14 -7
  354. package/dist/lib/session/session-cache.js +51 -9
  355. package/dist/lib/session/state.d.ts +2 -2
  356. package/dist/lib/session/state.js +1 -1
  357. package/dist/lib/session/sync/config.d.ts +10 -10
  358. package/dist/lib/session/sync/config.js +10 -10
  359. package/dist/lib/session/sync/r2.d.ts +34 -0
  360. package/dist/lib/session/sync/r2.js +123 -0
  361. package/dist/lib/session/throughput.d.ts +1 -1
  362. package/dist/lib/session/throughput.js +1 -1
  363. package/dist/lib/session/types.d.ts +23 -1
  364. package/dist/lib/session/types.js +15 -0
  365. package/dist/lib/session/viewing-in.d.ts +1 -1
  366. package/dist/lib/session/viewing-in.js +1 -1
  367. package/dist/lib/session/watch.d.ts +101 -0
  368. package/dist/lib/session/watch.js +242 -0
  369. package/dist/lib/share/config.d.ts +4 -0
  370. package/dist/lib/share/config.js +1 -0
  371. package/dist/lib/share/provision.d.ts +38 -0
  372. package/dist/lib/share/provision.js +50 -0
  373. package/dist/lib/share/publish.d.ts +40 -1
  374. package/dist/lib/share/publish.js +116 -3
  375. package/dist/lib/share/worker-template.js +71 -6
  376. package/dist/lib/shims.d.ts +17 -3
  377. package/dist/lib/shims.js +98 -26
  378. package/dist/lib/signin-badge.js +3 -2
  379. package/dist/lib/skills.js +2 -0
  380. package/dist/lib/smart-launch.d.ts +8 -8
  381. package/dist/lib/smart-launch.js +80 -59
  382. package/dist/lib/ssh-exec.d.ts +1 -1
  383. package/dist/lib/ssh-exec.js +1 -1
  384. package/dist/lib/staleness/prune.d.ts +88 -0
  385. package/dist/lib/staleness/prune.js +69 -0
  386. package/dist/lib/staleness/registry.d.ts +1 -1
  387. package/dist/lib/staleness/writers/commands.js +34 -2
  388. package/dist/lib/staleness/writers/hooks.js +16 -0
  389. package/dist/lib/staleness/writers/kinds.d.ts +6 -0
  390. package/dist/lib/staleness/writers/skills.js +19 -0
  391. package/dist/lib/staleness/writers/subagents.d.ts +2 -3
  392. package/dist/lib/staleness/writers/subagents.js +0 -4
  393. package/dist/lib/staleness/writers/types.d.ts +32 -0
  394. package/dist/lib/startup/command-registry.d.ts +6 -12
  395. package/dist/lib/startup/command-registry.js +11 -31
  396. package/dist/lib/startup/dev-build.d.ts +10 -0
  397. package/dist/lib/startup/dev-build.js +13 -1
  398. package/dist/lib/startup/spellcheck.d.ts +18 -0
  399. package/dist/lib/startup/spellcheck.js +45 -0
  400. package/dist/lib/state.d.ts +36 -9
  401. package/dist/lib/state.js +96 -46
  402. package/dist/lib/subagents-registry.d.ts +0 -7
  403. package/dist/lib/subagents-registry.js +38 -65
  404. package/dist/lib/subagents.d.ts +0 -33
  405. package/dist/lib/subagents.js +0 -75
  406. package/dist/lib/sync-umbrella.js +1 -1
  407. package/dist/lib/teams/agents.d.ts +41 -1
  408. package/dist/lib/teams/agents.js +187 -9
  409. package/dist/lib/teams/api.d.ts +11 -1
  410. package/dist/lib/teams/api.js +11 -2
  411. package/dist/lib/teams/delivery.d.ts +41 -0
  412. package/dist/lib/teams/delivery.js +60 -0
  413. package/dist/lib/teams/registry.d.ts +14 -0
  414. package/dist/lib/teams/registry.js +51 -1
  415. package/dist/lib/teams/remoteWorktree.d.ts +19 -0
  416. package/dist/lib/teams/remoteWorktree.js +29 -0
  417. package/dist/lib/teams/scheduler.d.ts +1 -1
  418. package/dist/lib/teams/scheduler.js +1 -1
  419. package/dist/lib/teams/worktree.d.ts +24 -0
  420. package/dist/lib/teams/worktree.js +42 -0
  421. package/dist/lib/terminal/backends/vscodium-agent.d.ts +10 -1
  422. package/dist/lib/terminal/backends/vscodium-agent.js +16 -5
  423. package/dist/lib/terminal/engine.d.ts +4 -0
  424. package/dist/lib/terminal/engine.js +8 -2
  425. package/dist/lib/terminal/types.d.ts +21 -2
  426. package/dist/lib/testdata/refresh-coordinator-worker.d.ts +1 -0
  427. package/dist/lib/testdata/refresh-coordinator-worker.js +23 -0
  428. package/dist/lib/tickets/list.d.ts +53 -0
  429. package/dist/lib/tickets/list.js +153 -0
  430. package/dist/lib/tmux/orphan-reap.d.ts +320 -0
  431. package/dist/lib/tmux/orphan-reap.js +644 -0
  432. package/dist/lib/tmux/session.d.ts +68 -3
  433. package/dist/lib/tmux/session.js +95 -5
  434. package/dist/lib/triggers/handlers.d.ts +20 -0
  435. package/dist/lib/triggers/handlers.js +6 -1
  436. package/dist/lib/types.d.ts +46 -34
  437. package/dist/lib/usage-fleet.d.ts +32 -0
  438. package/dist/lib/usage-fleet.js +125 -0
  439. package/dist/lib/usage-refresh.d.ts +3 -3
  440. package/dist/lib/usage-refresh.js +19 -16
  441. package/dist/lib/usage.d.ts +51 -47
  442. package/dist/lib/usage.js +145 -153
  443. package/dist/lib/version-duplicates.js +2 -2
  444. package/dist/lib/versions.d.ts +56 -13
  445. package/dist/lib/versions.js +195 -45
  446. package/dist/lib/watchdog/log.d.ts +1 -1
  447. package/dist/lib/watchdog/log.js +3 -3
  448. package/dist/lib/watchdog/rotate.d.ts +6 -6
  449. package/dist/lib/watchdog/rotate.js +6 -6
  450. package/dist/lib/workflows.d.ts +1 -1
  451. package/dist/lib/yaml-io.d.ts +47 -0
  452. package/dist/lib/yaml-io.js +55 -0
  453. package/package.json +2 -1
  454. package/scripts/install-helper.js +2 -2
  455. package/scripts/postinstall.js +23 -20
  456. package/dist/commands/defaults.d.ts +0 -7
  457. package/dist/commands/defaults.js +0 -107
  458. package/dist/commands/export.d.ts +0 -11
  459. package/dist/commands/export.js +0 -215
  460. package/dist/commands/helper.d.ts +0 -12
  461. package/dist/commands/helper.js +0 -87
  462. package/dist/commands/hosts.d.ts +0 -11
  463. package/dist/commands/hosts.js +0 -330
  464. package/dist/commands/lock.d.ts +0 -12
  465. package/dist/commands/lock.js +0 -70
  466. package/dist/commands/pull.d.ts +0 -17
  467. package/dist/commands/pull.js +0 -39
  468. package/dist/commands/push.d.ts +0 -14
  469. package/dist/commands/push.js +0 -30
  470. package/dist/commands/wallet.d.ts +0 -20
  471. package/dist/commands/wallet.js +0 -216
  472. package/dist/commands/worktree.d.ts +0 -19
  473. package/dist/commands/worktree.js +0 -272
  474. package/dist/lib/account-labels.d.ts +0 -24
  475. package/dist/lib/account-labels.js +0 -72
  476. package/dist/lib/auto-dispatch-linear.d.ts +0 -18
  477. package/dist/lib/auto-dispatch-linear.js +0 -107
  478. package/dist/lib/auto-dispatch-provider.d.ts +0 -10
  479. package/dist/lib/auto-dispatch-provider.js +0 -30
  480. package/dist/lib/auto-dispatch.d.ts +0 -93
  481. package/dist/lib/auto-dispatch.js +0 -128
  482. package/dist/lib/export.d.ts +0 -72
  483. package/dist/lib/export.js +0 -269
  484. package/dist/lib/lock.d.ts +0 -93
  485. package/dist/lib/lock.js +0 -207
  486. package/dist/lib/wallet/index.d.ts +0 -78
  487. package/dist/lib/wallet/index.js +0 -253
@@ -11,6 +11,7 @@ import { loadDevicesSync } from './devices/registry.js';
11
11
  import { normalizeHost } from './machine-id.js';
12
12
  import { probePoolSignals } from './teams/placement-probe.js';
13
13
  import { pickBestDevice } from './teams/scheduler.js';
14
+ import { getAccountInfo } from './agents.js';
14
15
  /** Peakiness of usage weights; >1 amplifies the most-used option. */
15
16
  export const DEFAULT_AFFINITY_ALPHA = 1.3;
16
17
  /**
@@ -64,38 +65,73 @@ export function listOnlineDeviceNames(localName = localMachineId()) {
64
65
  }
65
66
  return [...names];
66
67
  }
68
+ export function formatNoHealthyDeviceError(pool, signals, agent) {
69
+ const excluded = pool.map((key) => {
70
+ const signal = signals.get(key);
71
+ const reason = signal?.reachable !== true
72
+ ? 'unreachable'
73
+ : signal.headroom === 'loaded'
74
+ ? 'overloaded'
75
+ : signal.installed !== true || signal.signedIn !== true
76
+ ? 'no ready harness account'
77
+ : 'ineligible';
78
+ return `${key} (${reason})`;
79
+ }).join(', ');
80
+ const target = agent ? `can run ${agent}` : "for 'run auto'";
81
+ return `agents: no healthy device ${target} — excluded: ${excluded}; earliest window resets unknown`;
82
+ }
67
83
  /**
68
84
  * Pick the least-loaded healthy device that can run `agent` when the harness is
69
- * known. `run auto` omits the agent and ranks the same live health/load signals
70
- * without an installed-harness filter. The local machine participates in the
71
- * same probe; a fully unusable fleet degrades to local instead of stranding a run.
85
+ * known. `run auto` omits the agent and treats any ready account on the device
86
+ * as eligible. The local machine participates in the
87
+ * same probe and must pass the same eligibility checks. An empty eligible pool
88
+ * fails loud; automatic placement never silently becomes a local launch.
72
89
  */
73
90
  export async function resolveDeviceAuto(agent, opts = {}) {
74
91
  const local = normalizeHost(opts.localMachine ?? localMachineId());
75
92
  const pool = [...new Set((opts.eligibleHosts ?? listOnlineDeviceNames(local)).map(normalizeHost))];
76
93
  if (!pool.includes(local))
77
94
  pool.push(local);
78
- try {
79
- const signals = await (opts.probe ?? probePoolSignals)(pool, agent);
80
- const picked = pickBestDevice(pool, [], { signals, agentLabel: agent });
81
- return {
82
- host: picked === local ? null : picked,
83
- pickedDeviceKey: picked,
84
- candidates: pool.map((key) => ({
85
- key,
86
- loadPercent: signals.get(key)?.loadPercent,
87
- installed: signals.get(key)?.installed,
88
- signedIn: signals.get(key)?.signedIn,
89
- })),
90
- };
95
+ const signals = await (opts.probe ?? probePoolSignals)(pool, agent);
96
+ if (!agent && !opts.probe) {
97
+ const { collectFleetHarnesses } = await import('../commands/ssh.js');
98
+ const inventory = await collectFleetHarnesses({ devices: pool });
99
+ const byHost = new Map(inventory.map((result) => [normalizeHost(result.host), result]));
100
+ for (const key of pool) {
101
+ const result = byHost.get(key);
102
+ const accountEligible = !!result && !result.error && !result.skipped && result.rows.some((row) => row.ready);
103
+ const current = signals.get(key);
104
+ if (current)
105
+ signals.set(key, { ...current, installed: accountEligible, signedIn: accountEligible });
106
+ }
91
107
  }
92
- catch {
93
- return {
94
- host: null,
95
- pickedDeviceKey: local,
96
- candidates: [{ key: local }],
97
- };
108
+ if (agent && !opts.probe && signals.has(local)) {
109
+ const info = await getAccountInfo(agent).catch(() => null);
110
+ const eligible = !!info?.signedIn && info.usageStatus !== 'rate_limited' && info.usageStatus !== 'out_of_credits';
111
+ signals.set(local, { ...signals.get(local), signedIn: eligible });
98
112
  }
113
+ const eligiblePool = pool.filter((key) => {
114
+ const signal = signals.get(key);
115
+ if (signal?.reachable !== true || signal.headroom === 'loaded')
116
+ return false;
117
+ if (!agent)
118
+ return opts.probe ? true : signal.installed === true && signal.signedIn === true;
119
+ return signal.installed === true && signal.signedIn === true;
120
+ });
121
+ if (eligiblePool.length === 0) {
122
+ throw new Error(formatNoHealthyDeviceError(pool, signals, agent));
123
+ }
124
+ const picked = pickBestDevice(eligiblePool, [], { signals, agentLabel: agent });
125
+ return {
126
+ host: picked === local ? null : picked,
127
+ pickedDeviceKey: picked,
128
+ candidates: pool.map((key) => ({
129
+ key,
130
+ loadPercent: signals.get(key)?.loadPercent,
131
+ installed: signals.get(key)?.installed,
132
+ signedIn: signals.get(key)?.signedIn,
133
+ })),
134
+ };
99
135
  }
100
136
  /**
101
137
  * Resolve host for `--device auto`. Does NOT pick harness or accounts.
@@ -152,8 +188,8 @@ export function isDeviceAuto(value) {
152
188
  const HOST_SLOTS = ['host', 'device', 'on', 'computer'];
153
189
  /**
154
190
  * Apply `--device auto` / `--host auto` (and deprecated `--smart`) onto run options.
155
- * Mutates `options` in place. On affinity failure, clears auto slots (local) and
156
- * returns `skipped` never throws; callers must not hard-exit.
191
+ * Mutates `options` in place. Placement failures propagate without rewriting
192
+ * `auto`, so callers fail loud instead of silently launching locally.
157
193
  */
158
194
  export async function applyDeviceAutoToOptions(options, deps = {}) {
159
195
  let deprecationSmart = false;
@@ -167,42 +203,27 @@ export async function applyDeviceAutoToOptions(options, deps = {}) {
167
203
  if (!hasAuto) {
168
204
  return { attempted: false, deprecationSmart };
169
205
  }
170
- try {
171
- const resolve = deps.resolve ?? (() => resolveDeviceAuto(deps.agent));
172
- const plan = await resolve();
173
- const concrete = plan.host; // null = local
174
- for (const k of HOST_SLOTS) {
175
- if (isDeviceAuto(options[k])) {
176
- options[k] = concrete ?? undefined;
177
- }
206
+ const resolve = deps.resolve ?? (() => resolveDeviceAuto(deps.agent));
207
+ const plan = await resolve();
208
+ const concrete = plan.host; // null = local
209
+ for (const k of HOST_SLOTS) {
210
+ if (isDeviceAuto(options[k])) {
211
+ options[k] = concrete ?? undefined;
178
212
  }
179
- const accountPickerRequested = deps.accountPickerRequested ?? false;
180
- if (!accountPickerRequested && !options.strategy && !options.balanced) {
181
- options.balanced = true;
182
- }
183
- const hostLabel = concrete ?? 'local';
184
- const deviceHint = plan.candidates
185
- .slice(0, 4)
186
- .map((c) => `${c.key}:${c.loadPercent === undefined ? '?' : `${Math.round(c.loadPercent)}%`}`)
187
- .join(', ');
188
- const acctNote = accountPickerRequested ? 'accounts=picker' : 'accounts=balanced';
189
- return {
190
- attempted: true,
191
- deprecationSmart,
192
- banner: { hostLabel, deviceHint, acctNote },
193
- };
194
213
  }
195
- catch (err) {
196
- // Graceful degrade: clear auto slots so the run continues locally.
197
- for (const k of HOST_SLOTS) {
198
- if (isDeviceAuto(options[k])) {
199
- options[k] = undefined;
200
- }
201
- }
202
- return {
203
- attempted: true,
204
- deprecationSmart,
205
- skipped: err.message,
206
- };
214
+ const accountPickerRequested = deps.accountPickerRequested ?? false;
215
+ if (!accountPickerRequested && !options.strategy && !options.balanced) {
216
+ options.balanced = true;
207
217
  }
218
+ const hostLabel = concrete ?? 'local';
219
+ const deviceHint = plan.candidates
220
+ .slice(0, 4)
221
+ .map((c) => `${c.key}:${c.loadPercent === undefined ? '?' : `${Math.round(c.loadPercent)}%`}`)
222
+ .join(', ');
223
+ const acctNote = accountPickerRequested ? 'accounts=picker' : 'accounts=balanced';
224
+ return {
225
+ attempted: true,
226
+ deprecationSmart,
227
+ banner: { hostLabel, deviceHint, acctNote },
228
+ };
208
229
  }
@@ -2,7 +2,7 @@
2
2
  * Shared SSH exec primitive — the single hardened choke point for running a
3
3
  * command on a remote host over the system `ssh`.
4
4
  *
5
- * `agents hosts` dispatch and the browser driver both go through here so the
5
+ * `agents run --host` dispatch and the browser driver both go through here so the
6
6
  * connection hardening (`BatchMode`, `accept-new`, `ConnectTimeout`) and the
7
7
  * target-injection guard live in exactly one place. Target validation is the
8
8
  * canonical definition; `commands/secrets.ts` re-exports it.
@@ -2,7 +2,7 @@
2
2
  * Shared SSH exec primitive — the single hardened choke point for running a
3
3
  * command on a remote host over the system `ssh`.
4
4
  *
5
- * `agents hosts` dispatch and the browser driver both go through here so the
5
+ * `agents run --host` dispatch and the browser driver both go through here so the
6
6
  * connection hardening (`BatchMode`, `accept-new`, `ConnectTimeout`) and the
7
7
  * target-injection guard live in exactly one place. Target validation is the
8
8
  * canonical definition; `commands/secrets.ts` re-exports it.
@@ -0,0 +1,88 @@
1
+ /**
2
+ * Manifest-bounded prune (RUSH-2438).
3
+ *
4
+ * `agents sync` was additive-only: it installed/updated resources present in
5
+ * source but never removed a resource that had been DELETED from source, so a
6
+ * removed command/skill/hook lingered in every installed version home forever
7
+ * (and stayed live in the `/` menu). Bare `agents sync <agent>` full syncs did
8
+ * sweep orphans, but the repo-scoped forms the reconcile path actually uses —
9
+ * `agents sync <agent>@all system`, `agents sync <agent> system --force` — pass
10
+ * a selection, which turned the orphan sweeps off. This closes that gap.
11
+ *
12
+ * The prune set is computed by name, bounded by the sync manifest:
13
+ *
14
+ * prune = (names the last sync recorded as installed)
15
+ * − (names still present in source across ALL layers)
16
+ * ∩ (names currently materialized in the version home)
17
+ *
18
+ * Each clause is a safety guarantee:
19
+ * - The manifest bound means only agents-installed resources are ever
20
+ * candidates — a file the user hand-authored into the version home was
21
+ * never recorded, so it is never touched.
22
+ * - Diffing against ALL layers (not just the scoped one) means a resource
23
+ * still provided by any other layer — e.g. a same-named user command that
24
+ * shadows a removed system command — stays: it is still "in source".
25
+ * - Requiring the name to be materialized skips work for anything already
26
+ * gone and never errors on a missing path.
27
+ *
28
+ * When there is NO manifest we cannot know what a prior sync installed, so we
29
+ * FAIL LOUD by pruning nothing and reporting it — never a "delete everything
30
+ * not in source" guess. The manifest is written by the next full sync, so the
31
+ * baseline heals itself.
32
+ *
33
+ * Deletion itself is delegated to each writer's `remove()` (the inverse of
34
+ * `write()`), so per-harness layout knowledge — native file vs command-skill
35
+ * dir vs goose recipe — lives in one place and can't drift.
36
+ */
37
+ import type { AgentId } from '../types.js';
38
+ import type { SyncManifest } from './types.js';
39
+ /**
40
+ * Kinds prune reconciles. Restricted to the name-keyed file/dir resources whose
41
+ * writer implements `remove()`. Deliberately excluded, each with a reason:
42
+ * - hooks — a version-home hook script is coupled to a settings.json /
43
+ * hooks.json REGISTRATION. Pruning the last hook to zero would delete the
44
+ * script but must also GC its registration in the same pass, and that lands
45
+ * in `src/lib/hooks.ts` — a Windows-portable-path surface the CI windows leg
46
+ * gates on. Split to RUSH-2456 so this PR stays Linux-only-green; hook FILES
47
+ * are still reconciled by the in-write orphan sweep (versions.ts, gated on
48
+ * `hooksToSync > 0`).
49
+ * - rules / permissions — synced as a wholesale rewrite (one composed file /
50
+ * the full allowlist), so a removed rule or group already drops out.
51
+ * - plugins — carry their own reconciliation via `cleanOrphanedPluginSkills`.
52
+ * - mcp — registered through each agent's CLI/config, a separate removal path.
53
+ * - subagents / workflows — no clean per-name inverse yet (multi-agent index
54
+ * finalize; native workflow trees); tracked for a follow-up.
55
+ */
56
+ export declare const PRUNABLE_KINDS: readonly ["commands", "skills"];
57
+ export type PrunableKind = typeof PRUNABLE_KINDS[number];
58
+ export interface PruneInput {
59
+ agent: AgentId;
60
+ version: string;
61
+ versionHome: string;
62
+ cwd: string;
63
+ /**
64
+ * The sync manifest loaded BEFORE this sync ran — the record of what the last
65
+ * sync installed. `null` means no prior full sync established a baseline.
66
+ */
67
+ previousManifest: SyncManifest | null;
68
+ /**
69
+ * Current source resource names across ALL layers (project/user/system/extras),
70
+ * per prunable kind. A name present here is still "in source" and never pruned.
71
+ */
72
+ sourceNames: Record<PrunableKind, ReadonlyArray<string>>;
73
+ }
74
+ export interface PruneOutcome {
75
+ /** Names actually removed from the version home, per kind. */
76
+ pruned: Record<PrunableKind, string[]>;
77
+ /**
78
+ * True when prune ran with no manifest and therefore deleted nothing — the
79
+ * fail-loud baseline case. Callers surface this so a skipped reconcile is
80
+ * never mistaken for "nothing to prune".
81
+ */
82
+ skippedNoManifest: boolean;
83
+ }
84
+ /**
85
+ * Remove resources that a prior sync installed and that are now gone from
86
+ * source, from one agent@version home. Deletes nothing when no manifest exists.
87
+ */
88
+ export declare function pruneRemovedResources(input: PruneInput): PruneOutcome;
@@ -0,0 +1,69 @@
1
+ import { getWriter, getDetector } from './registry.js';
2
+ /**
3
+ * Kinds prune reconciles. Restricted to the name-keyed file/dir resources whose
4
+ * writer implements `remove()`. Deliberately excluded, each with a reason:
5
+ * - hooks — a version-home hook script is coupled to a settings.json /
6
+ * hooks.json REGISTRATION. Pruning the last hook to zero would delete the
7
+ * script but must also GC its registration in the same pass, and that lands
8
+ * in `src/lib/hooks.ts` — a Windows-portable-path surface the CI windows leg
9
+ * gates on. Split to RUSH-2456 so this PR stays Linux-only-green; hook FILES
10
+ * are still reconciled by the in-write orphan sweep (versions.ts, gated on
11
+ * `hooksToSync > 0`).
12
+ * - rules / permissions — synced as a wholesale rewrite (one composed file /
13
+ * the full allowlist), so a removed rule or group already drops out.
14
+ * - plugins — carry their own reconciliation via `cleanOrphanedPluginSkills`.
15
+ * - mcp — registered through each agent's CLI/config, a separate removal path.
16
+ * - subagents / workflows — no clean per-name inverse yet (multi-agent index
17
+ * finalize; native workflow trees); tracked for a follow-up.
18
+ */
19
+ export const PRUNABLE_KINDS = ['commands', 'skills'];
20
+ /** Names the manifest recorded as installed for a kind (source-name keyed). */
21
+ function manifestNames(manifest, kind) {
22
+ switch (kind) {
23
+ case 'commands': {
24
+ // Object keys are the source command names; writtenCommands carries any
25
+ // extra names the writer actually emitted (dual-write / command-skill).
26
+ const names = new Set(Object.keys(manifest.commands ?? {}));
27
+ for (const c of manifest.writtenCommands ?? [])
28
+ names.add(c);
29
+ return [...names];
30
+ }
31
+ case 'skills': return Object.keys(manifest.skills ?? {});
32
+ }
33
+ }
34
+ function emptyPruned() {
35
+ return { commands: [], skills: [] };
36
+ }
37
+ /**
38
+ * Remove resources that a prior sync installed and that are now gone from
39
+ * source, from one agent@version home. Deletes nothing when no manifest exists.
40
+ */
41
+ export function pruneRemovedResources(input) {
42
+ const { agent, version, versionHome, cwd, previousManifest, sourceNames } = input;
43
+ if (!previousManifest) {
44
+ return { pruned: emptyPruned(), skippedNoManifest: true };
45
+ }
46
+ const pruned = emptyPruned();
47
+ for (const kind of PRUNABLE_KINDS) {
48
+ const writer = getWriter(kind, agent);
49
+ const detector = getDetector(kind, agent);
50
+ // No writer.remove (unsupported kind/agent) or no detector: nothing to do.
51
+ if (!writer?.remove || !detector)
52
+ continue;
53
+ const installed = manifestNames(previousManifest, kind);
54
+ if (installed.length === 0)
55
+ continue;
56
+ const stillInSource = new Set(sourceNames[kind]);
57
+ const materialized = new Set(detector.list({ version, versionHome, cwd }));
58
+ for (const name of installed) {
59
+ if (stillInSource.has(name))
60
+ continue; // still provided by some layer
61
+ if (!materialized.has(name))
62
+ continue; // already gone from the home
63
+ const result = writer.remove({ version, versionHome, name, cwd });
64
+ if (result.removed)
65
+ pruned[kind].push(name);
66
+ }
67
+ }
68
+ return { pruned, skippedNoManifest: false };
69
+ }
@@ -5,7 +5,7 @@ import type { ResourceDetector } from './detectors/types.js';
5
5
  import type { RulesSelection } from './writers/rules.js';
6
6
  export type { ResourceKind } from './writers/kinds.js';
7
7
  export { kindToCapability, ALL_RESOURCE_KINDS } from './writers/kinds.js';
8
- export type { ResourceWriter, WriteArgs, WriteResult } from './writers/types.js';
8
+ export type { ResourceWriter, WriteArgs, WriteResult, RemoveArgs, RemoveResult } from './writers/types.js';
9
9
  export type { ResourceDetector, DetectArgs } from './detectors/types.js';
10
10
  export type { RulesSelection } from './writers/rules.js';
11
11
  /** Per-kind selection payload. Most kinds are string[]; rules is special. */
@@ -25,8 +25,8 @@ import { supports } from '../../capabilities.js';
25
25
  import { safeJoin } from '../../paths.js';
26
26
  import { markdownToToml } from '../../convert.js';
27
27
  import { commandAppliesTo, parseCommandMetadata } from '../../commands.js';
28
- import { installCommandSkillToVersion, shouldAlsoInstallCommandAsSkill, shouldInstallCommandAsSkill, } from '../../command-skills.js';
29
- import { installGooseCommandToVersion } from '../../goose-commands.js';
28
+ import { installCommandSkillToVersion, listCommandSkillsInVersion, removeCommandSkillFromVersion, shouldAlsoInstallCommandAsSkill, shouldInstallCommandAsSkill, } from '../../command-skills.js';
29
+ import { installGooseCommandToVersion, listGooseCommandsInVersion, removeGooseCommandFromVersion, } from '../../goose-commands.js';
30
30
  import { resolveCommandSource, trustedSkillRoots } from './sources.js';
31
31
  import { lazyAgentMap } from './lazy-map.js';
32
32
  function buildCommandsWriter(agent) {
@@ -82,6 +82,38 @@ function buildCommandsWriter(agent) {
82
82
  }
83
83
  return { synced };
84
84
  },
85
+ remove({ versionHome, name }) {
86
+ const agentConfig = AGENTS[agent];
87
+ const agentDir = path.join(versionHome, agentConfigDirName(agent));
88
+ let removed = false;
89
+ // Native command file (Claude, Codex <0.117, Grok, Cursor, …). The
90
+ // extension follows the agent's format, mirroring the write path above.
91
+ if (agentConfig.commandsSubdir) {
92
+ const ext = agentConfig.format === 'toml' ? '.toml' : '.md';
93
+ const nativeFile = safeJoin(path.join(agentDir, agentConfig.commandsSubdir), `${name}${ext}`);
94
+ try {
95
+ if (fs.existsSync(nativeFile) && fs.lstatSync(nativeFile).isFile()) {
96
+ fs.unlinkSync(nativeFile);
97
+ removed = true;
98
+ }
99
+ }
100
+ catch { /* already gone / inaccessible */ }
101
+ }
102
+ // Command-as-skill dir (Codex >=0.117, Kimi; Cursor dual-write). Gated on
103
+ // it currently being a command-skill, and removeCommandSkillFromVersion
104
+ // re-checks the `agents_command` marker before deleting — so a real skill
105
+ // of the same name is never destroyed by a command prune.
106
+ if (listCommandSkillsInVersion(agentDir).includes(name)) {
107
+ if (removeCommandSkillFromVersion(agentDir, name).success)
108
+ removed = true;
109
+ }
110
+ // Goose recipe YAML + its slash_commands registry entry.
111
+ if (agent === 'goose' && listGooseCommandsInVersion(versionHome).includes(name)) {
112
+ if (removeGooseCommandFromVersion(versionHome, name).success)
113
+ removed = true;
114
+ }
115
+ return { removed };
116
+ },
85
117
  };
86
118
  }
87
119
  // Built lazily on first access — see lazy-map.ts for the cycle rationale.
@@ -95,6 +95,22 @@ function buildHooksWriter(agent) {
95
95
  }
96
96
  return { synced };
97
97
  },
98
+ remove({ versionHome, name }) {
99
+ // Delete the copied hook artifact from `{agentDir}/hooks/<name>`. Native
100
+ // settings.json/hooks.json registration is regenerated by the write path
101
+ // that runs alongside this prune (registerHooksToSettings above reads the
102
+ // remaining source manifest), so a removed hook drops out of both.
103
+ const agentDir = path.join(versionHome, agentConfigDirName(agent));
104
+ const hookTarget = safeJoin(path.join(agentDir, 'hooks'), name);
105
+ try {
106
+ if (fs.existsSync(hookTarget)) {
107
+ removePath(hookTarget);
108
+ return { removed: true };
109
+ }
110
+ }
111
+ catch { /* already gone / inaccessible */ }
112
+ return { removed: false };
113
+ },
98
114
  };
99
115
  }
100
116
  export const hooksWriters = lazyAgentMap(() => {
@@ -2,6 +2,12 @@
2
2
  * Canonical list of resource kinds dispatched through the writer/detector
3
3
  * registry. Each name is the capability name on AgentConfig — except
4
4
  * "permissions", which maps to the legacy capability name "allowlist".
5
+ *
6
+ * NOTE: "rules" in this registry is the WRITER key for what ResourceSelection
7
+ * calls "memory". The --rule/--rules CLI flag therefore maps to the "memory"
8
+ * key in ResourceSelection, not to a key called "rules". The memory file is
9
+ * composed from all layers (not a per-repo artifact), so it is always set to
10
+ * 'all' rather than filtered by individual names.
5
11
  */
6
12
  import type { CapabilityName } from '../../types.js';
7
13
  export type ResourceKind = 'commands' | 'skills' | 'hooks' | 'rules' | 'mcp' | 'permissions' | 'subagents' | 'plugins' | 'workflows';
@@ -9,6 +9,7 @@ import * as path from 'path';
9
9
  import { AGENTS, agentConfigDirName } from '../../agents.js';
10
10
  import { capableAgents } from '../../capabilities.js';
11
11
  import { safeJoin } from '../../paths.js';
12
+ import { listCommandSkillsInVersion } from '../../command-skills.js';
12
13
  import { resolveSkillSource } from './sources.js';
13
14
  import { lazyAgentMap } from './lazy-map.js';
14
15
  const SKILL_COPY_IGNORE = new Set(['.DS_Store', '.git', '.gitignore', '.venv', '__pycache__', 'node_modules']);
@@ -66,6 +67,24 @@ function buildSkillsWriter(agent) {
66
67
  }
67
68
  return { synced };
68
69
  },
70
+ remove({ versionHome, name }) {
71
+ const agentDir = path.join(versionHome, agentConfigDirName(agent));
72
+ // A command-installed-as-skill lives in the same skills/ dir but is owned
73
+ // by the commands writer's prune — never delete it from here, or a
74
+ // still-live converted command would vanish under a skill prune.
75
+ if (listCommandSkillsInVersion(agentDir).includes(name)) {
76
+ return { removed: false };
77
+ }
78
+ const destDir = safeJoin(path.join(agentDir, 'skills'), name);
79
+ try {
80
+ if (fs.existsSync(destDir) && fs.lstatSync(destDir).isDirectory()) {
81
+ removePath(destDir);
82
+ return { removed: true };
83
+ }
84
+ }
85
+ catch { /* already gone / inaccessible */ }
86
+ return { removed: false };
87
+ },
69
88
  };
70
89
  }
71
90
  export const skillsWriters = lazyAgentMap(() => {
@@ -1,8 +1,7 @@
1
1
  /**
2
2
  * Subagents writer. Every agent's on-disk layout (target dir, file/dir shape,
3
- * transform, and any post-sync finalize such as Kimi's parent index) is
4
- * declared once in the subagent registry; this writer is generic and iterates
5
- * the registry instead of a per-agent `else if` chain.
3
+ * transform) is declared once in the subagent registry; this writer is generic
4
+ * and iterates the registry instead of a per-agent `else if` chain.
6
5
  *
7
6
  * Source-side discovery is `listInstalledSubagents` from lib/subagents.ts —
8
7
  * it reads user + system layers only (project layer excluded for the same
@@ -24,10 +24,6 @@ function buildSubagentsWriter(agent) {
24
24
  }
25
25
  catch { /* per-item sync failure: skip */ }
26
26
  }
27
- // Optional cross-item pass (e.g. Kimi's `_agents-cli.yaml` parent index).
28
- if (target.finalize && synced.length > 0) {
29
- target.finalize(dir, synced.map((name) => map.get(name)));
30
- }
31
27
  return { synced };
32
28
  },
33
29
  };
@@ -29,8 +29,40 @@ export interface WriteResult {
29
29
  /** Names actually written. Empty array = write produced nothing (not an error). */
30
30
  synced: string[];
31
31
  }
32
+ /**
33
+ * Inverse of a write: locate and delete the materialized artifact for one
34
+ * resource `name` from a version home. Used only by the manifest-bounded prune
35
+ * pass (RUSH-2438), which supplies names it has already proven were
36
+ * agents-installed and are gone from source — the writer just owns the layout
37
+ * knowledge (native file vs command-skill dir vs recipe) so prune never
38
+ * re-derives it.
39
+ */
40
+ export interface RemoveArgs {
41
+ /** Agent version (e.g. "1.2.3"). */
42
+ version: string;
43
+ /** Absolute path to the version's home dir. */
44
+ versionHome: string;
45
+ /** Resource name to remove (no extension). */
46
+ name: string;
47
+ /** Current working directory — used by writers that consult project-layer state. */
48
+ cwd: string;
49
+ }
50
+ export interface RemoveResult {
51
+ /** True when an artifact owned by this writer was found and deleted. */
52
+ removed: boolean;
53
+ }
32
54
  export interface ResourceWriter<Sel = string[]> {
33
55
  readonly kind: ResourceKind;
34
56
  readonly agent: AgentId;
35
57
  write(args: WriteArgs<Sel>): WriteResult;
58
+ /**
59
+ * Optional inverse of `write` for the prune pass. Only the name-keyed
60
+ * file/dir kinds implement it (commands, skills, hooks); kinds whose sync is
61
+ * a wholesale rewrite (rules, permissions) or that carry their own
62
+ * reconciliation (plugins via cleanOrphanedPluginSkills) leave it undefined.
63
+ * Absence is not a silent skip: `pruneRemovedResources` only iterates
64
+ * `PRUNABLE_KINDS`, and a registry completeness test asserts every writer for
65
+ * those kinds implements `remove`.
66
+ */
67
+ remove?(args: RemoveArgs): RemoveResult;
36
68
  }
@@ -37,20 +37,19 @@ export declare const loadCli: ModuleLoader;
37
37
  export declare const loadSubagents: ModuleLoader;
38
38
  export declare const loadPlugins: ModuleLoader;
39
39
  export declare const loadWorkflows: ModuleLoader;
40
- export declare const loadWorktree: ModuleLoader;
41
40
  export declare const loadVersions: ModuleLoader;
42
41
  export declare const loadUpdate: ModuleLoader;
43
42
  export declare const loadImport: ModuleLoader;
44
- export declare const loadExport: ModuleLoader;
45
43
  export declare const loadPackages: ModuleLoader;
46
44
  export declare const loadRoutines: ModuleLoader;
47
45
  export declare const loadMonitors: ModuleLoader;
48
46
  export declare const loadProjects: ModuleLoader;
49
47
  export declare const loadRun: ModuleLoader;
50
48
  export declare const loadResume: ModuleLoader;
49
+ export declare const loadOpen: ModuleLoader;
51
50
  export declare const loadReconnect: ModuleLoader;
52
51
  export declare const loadFork: ModuleLoader;
53
- export declare const loadDefaults: ModuleLoader;
52
+ export declare const loadConfig: ModuleLoader;
54
53
  export declare const loadSet: ModuleLoader;
55
54
  export declare const loadModels: ModuleLoader;
56
55
  export declare const loadModes: ModuleLoader;
@@ -65,12 +64,9 @@ export declare const loadProfiles: ModuleLoader;
65
64
  export declare const loadHarness: ModuleLoader;
66
65
  export declare const loadSecrets: ModuleLoader;
67
66
  export declare const loadLogin: ModuleLoader;
68
- export declare const loadWallet: ModuleLoader;
69
- export declare const loadHelper: ModuleLoader;
70
67
  export declare const loadMenubar: ModuleLoader;
71
68
  export declare const loadBeta: ModuleLoader;
72
69
  export declare const loadSync: ModuleLoader;
73
- export declare const loadLock: ModuleLoader;
74
70
  export declare const loadRefreshRules: ModuleLoader;
75
71
  export declare const loadFactory: ModuleLoader;
76
72
  export declare const loadUsage: ModuleLoader;
@@ -88,19 +84,16 @@ export declare const loadTmux: ModuleLoader;
88
84
  export declare const loadWatchdog: ModuleLoader;
89
85
  export declare const loadBrowser: ModuleLoader;
90
86
  export declare const loadComputer: ModuleLoader;
91
- export declare const loadHosts: ModuleLoader;
92
- export declare const loadLease: ModuleLoader;
93
87
  export declare const loadLogs: ModuleLoader;
94
88
  export declare const loadEvents: ModuleLoader;
95
89
  export declare const loadSsh: ModuleLoader;
96
- export declare const loadPull: ModuleLoader;
97
- export declare const loadPush: ModuleLoader;
98
90
  export declare const loadRepo: ModuleLoader;
99
91
  export declare const loadSetup: ModuleLoader;
100
92
  export declare const loadUninstall: ModuleLoader;
101
93
  export declare const loadUpgrade: ModuleLoader;
102
94
  export declare const loadSessions: ModuleLoader;
103
95
  export declare const loadTeams: ModuleLoader;
96
+ export declare const loadTickets: ModuleLoader;
104
97
  export declare const loadCloud: ModuleLoader;
105
98
  export declare const loadMessage: ModuleLoader;
106
99
  export declare const loadSend: ModuleLoader;
@@ -109,11 +102,11 @@ export declare const loadMailboxes: ModuleLoader;
109
102
  export declare const loadServe: ModuleLoader;
110
103
  export declare const loadShare: ModuleLoader;
111
104
  export declare const loadAudit: ModuleLoader;
112
- export declare const loadWebhook: ModuleLoader;
113
- export declare const loadFunnel: ModuleLoader;
105
+ export declare const loadWebhooks: ModuleLoader;
114
106
  export declare const loadHumans: ModuleLoader;
115
107
  export declare const loadAccounts: ModuleLoader;
116
108
  export declare const loadDaemon: ModuleLoader;
109
+ export declare const loadCp: ModuleLoader;
117
110
  /**
118
111
  * Commands whose modules pull in the SQLite-backed session/cloud stack. They are
119
112
  * registered AFTER `applyGlobalHelpConventions` (mirroring main's order: help
@@ -150,6 +143,7 @@ export declare const COMMAND_LOADERS: Record<string, ModuleLoader[]>;
150
143
  * registered command tree so a new command can never drift out of it.
151
144
  */
152
145
  export declare const KNOWN_TOP_LEVEL_COMMANDS: ReadonlySet<string>;
146
+ export declare const RETIRED_TOP_LEVEL_COMMANDS: ReadonlySet<string>;
153
147
  /** Whether `name` is a top-level command this CLI registers. See {@link KNOWN_TOP_LEVEL_COMMANDS}. */
154
148
  export declare function isKnownTopLevelCommand(name: string): boolean;
155
149
  /**