borgmcp 1.1.15 → 2.0.2

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 (466) hide show
  1. package/CONTRIBUTING.md +15 -0
  2. package/LICENSE +201 -33
  3. package/NOTICE +2 -0
  4. package/README.md +85 -36
  5. package/SECURITY.md +7 -0
  6. package/dist/agent-runtime.d.ts.map +1 -0
  7. package/dist/agent-runtime.js +63 -1
  8. package/dist/agent-runtime.js.map +1 -0
  9. package/dist/assimilate-cmd.d.ts +96 -17
  10. package/dist/assimilate-cmd.d.ts.map +1 -0
  11. package/dist/assimilate-cmd.js +1396 -48
  12. package/dist/assimilate-cmd.js.map +1 -0
  13. package/dist/assimilate-deps.d.ts.map +1 -0
  14. package/dist/assimilate-deps.js +384 -3
  15. package/dist/assimilate-deps.js.map +1 -0
  16. package/dist/assimilate-guard.d.ts +5 -7
  17. package/dist/assimilate-guard.d.ts.map +1 -0
  18. package/dist/assimilate-guard.js +60 -2
  19. package/dist/assimilate-guard.js.map +1 -0
  20. package/dist/assimilate-welcome.d.ts +1 -1
  21. package/dist/assimilate-welcome.d.ts.map +1 -0
  22. package/dist/assimilate-welcome.js +32 -2
  23. package/dist/assimilate-welcome.js.map +1 -0
  24. package/dist/auth-env.d.ts +7 -50
  25. package/dist/auth-env.d.ts.map +1 -0
  26. package/dist/auth-env.js +22 -1
  27. package/dist/auth-env.js.map +1 -0
  28. package/dist/backends/launch-all-pastelist.d.ts.map +1 -0
  29. package/dist/backends/launch-all-pastelist.js +11 -4
  30. package/dist/backends/launch-all-pastelist.js.map +1 -0
  31. package/dist/backends/launch-all-tmux.d.ts.map +1 -0
  32. package/dist/backends/launch-all-tmux.js +49 -1
  33. package/dist/backends/launch-all-tmux.js.map +1 -0
  34. package/dist/backends/launch-all-windows.d.ts.map +1 -0
  35. package/dist/backends/launch-all-windows.js +86 -12
  36. package/dist/backends/launch-all-windows.js.map +1 -0
  37. package/dist/bare-launch-menu.d.ts.map +1 -0
  38. package/dist/bare-launch-menu.js +83 -6
  39. package/dist/bare-launch-menu.js.map +1 -0
  40. package/dist/claude-launch-args.d.ts.map +1 -0
  41. package/dist/claude-launch-args.js +34 -1
  42. package/dist/claude-launch-args.js.map +1 -0
  43. package/dist/claude.d.ts.map +1 -0
  44. package/dist/claude.js +486 -14
  45. package/dist/claude.js.map +1 -0
  46. package/dist/cleanup-cmd.d.ts +5 -5
  47. package/dist/cleanup-cmd.d.ts.map +1 -0
  48. package/dist/cleanup-cmd.js +453 -14
  49. package/dist/cleanup-cmd.js.map +1 -0
  50. package/dist/clear-rewake-core.d.ts.map +1 -0
  51. package/dist/clear-rewake-core.js +23 -2
  52. package/dist/clear-rewake-core.js.map +1 -0
  53. package/dist/clear-rewake.d.ts.map +1 -0
  54. package/dist/clear-rewake.js +19 -1
  55. package/dist/clear-rewake.js.map +1 -0
  56. package/dist/cli-help.d.ts +5 -0
  57. package/dist/cli-help.d.ts.map +1 -0
  58. package/dist/cli-help.js +104 -56
  59. package/dist/cli-help.js.map +1 -0
  60. package/dist/cli-platform.d.ts.map +1 -0
  61. package/dist/cli-platform.js +106 -4
  62. package/dist/cli-platform.js.map +1 -0
  63. package/dist/cli-tool-approval.d.ts +84 -0
  64. package/dist/cli-tool-approval.d.ts.map +1 -0
  65. package/dist/cli-tool-approval.js +583 -0
  66. package/dist/cli-tool-approval.js.map +1 -0
  67. package/dist/codex-app-server.d.ts.map +1 -0
  68. package/dist/codex-app-server.js +228 -4
  69. package/dist/codex-app-server.js.map +1 -0
  70. package/dist/codex-app-wake.d.ts +9 -11
  71. package/dist/codex-app-wake.d.ts.map +1 -0
  72. package/dist/codex-app-wake.js +436 -2
  73. package/dist/codex-app-wake.js.map +1 -0
  74. package/dist/codex-launch.d.ts.map +1 -0
  75. package/dist/codex-launch.js +102 -2
  76. package/dist/codex-launch.js.map +1 -0
  77. package/dist/codex-remote.d.ts +6 -1
  78. package/dist/codex-remote.d.ts.map +1 -0
  79. package/dist/codex-remote.js +394 -1
  80. package/dist/codex-remote.js.map +1 -0
  81. package/dist/codex-wake-resolve.d.ts +4 -4
  82. package/dist/codex-wake-resolve.d.ts.map +1 -0
  83. package/dist/codex-wake-resolve.js +127 -1
  84. package/dist/codex-wake-resolve.js.map +1 -0
  85. package/dist/config-utils.d.ts +2 -2
  86. package/dist/config-utils.d.ts.map +1 -0
  87. package/dist/config-utils.js +766 -3
  88. package/dist/config-utils.js.map +1 -0
  89. package/dist/config.d.ts +98 -61
  90. package/dist/config.d.ts.map +1 -0
  91. package/dist/config.js +426 -1
  92. package/dist/config.js.map +1 -0
  93. package/dist/console-prefix.d.ts.map +1 -0
  94. package/dist/console-prefix.js +96 -1
  95. package/dist/console-prefix.js.map +1 -0
  96. package/dist/cube-name.d.ts.map +1 -0
  97. package/dist/cube-name.js +67 -1
  98. package/dist/cube-name.js.map +1 -0
  99. package/dist/cubes.d.ts +126 -18
  100. package/dist/cubes.d.ts.map +1 -0
  101. package/dist/cubes.js +412 -4
  102. package/dist/cubes.js.map +1 -0
  103. package/dist/debug.d.ts.map +1 -0
  104. package/dist/debug.js +71 -1
  105. package/dist/debug.js.map +1 -0
  106. package/dist/direct-log.d.ts.map +1 -0
  107. package/dist/direct-log.js +11 -1
  108. package/dist/direct-log.js.map +1 -0
  109. package/dist/docs-sections.d.ts +11 -10
  110. package/dist/docs-sections.d.ts.map +1 -0
  111. package/dist/docs-sections.js +113 -3
  112. package/dist/docs-sections.js.map +1 -0
  113. package/dist/drone-lifecycle.d.ts +5 -21
  114. package/dist/drone-lifecycle.d.ts.map +1 -0
  115. package/dist/drone-lifecycle.js +57 -8
  116. package/dist/drone-lifecycle.js.map +1 -0
  117. package/dist/drone-management.d.ts +29 -0
  118. package/dist/drone-management.d.ts.map +1 -0
  119. package/dist/drone-management.js +109 -0
  120. package/dist/drone-management.js.map +1 -0
  121. package/dist/ensure-mcp-config.d.ts.map +1 -0
  122. package/dist/ensure-mcp-config.js +36 -1
  123. package/dist/ensure-mcp-config.js.map +1 -0
  124. package/dist/evict-drone.d.ts +10 -2
  125. package/dist/evict-drone.d.ts.map +1 -0
  126. package/dist/evict-drone.js +60 -1
  127. package/dist/evict-drone.js.map +1 -0
  128. package/dist/gc-orphan-inboxes.d.ts.map +1 -0
  129. package/dist/gc-orphan-inboxes.js +177 -1
  130. package/dist/gc-orphan-inboxes.js.map +1 -0
  131. package/dist/inbox-monitor.d.ts +1 -1
  132. package/dist/inbox-monitor.d.ts.map +1 -0
  133. package/dist/inbox-monitor.js +856 -3
  134. package/dist/inbox-monitor.js.map +1 -0
  135. package/dist/index.d.ts +6 -4
  136. package/dist/index.d.ts.map +1 -0
  137. package/dist/index.js +1034 -37
  138. package/dist/index.js.map +1 -0
  139. package/dist/launch-all-cmd.d.ts.map +1 -0
  140. package/dist/launch-all-cmd.js +377 -37
  141. package/dist/launch-all-cmd.js.map +1 -0
  142. package/dist/launch-all-command.d.ts.map +1 -0
  143. package/dist/launch-all-command.js +24 -1
  144. package/dist/launch-all-command.js.map +1 -0
  145. package/dist/launch-all-deps.d.ts +3 -8
  146. package/dist/launch-all-deps.d.ts.map +1 -0
  147. package/dist/launch-all-deps.js +99 -1
  148. package/dist/launch-all-deps.js.map +1 -0
  149. package/dist/launch-all-discovery.d.ts +1 -0
  150. package/dist/launch-all-discovery.d.ts.map +1 -0
  151. package/dist/launch-all-discovery.js +90 -4
  152. package/dist/launch-all-discovery.js.map +1 -0
  153. package/dist/launch-all-locks.d.ts.map +1 -0
  154. package/dist/launch-all-locks.js +54 -1
  155. package/dist/launch-all-locks.js.map +1 -0
  156. package/dist/launch-gate.d.ts +2 -2
  157. package/dist/launch-gate.d.ts.map +1 -0
  158. package/dist/launch-gate.js +73 -1
  159. package/dist/launch-gate.js.map +1 -0
  160. package/dist/lifecycle-log-guard.d.ts.map +1 -0
  161. package/dist/lifecycle-log-guard.js +93 -2
  162. package/dist/lifecycle-log-guard.js.map +1 -0
  163. package/dist/list-roles-render.d.ts.map +1 -0
  164. package/dist/list-roles-render.js +40 -6
  165. package/dist/list-roles-render.js.map +1 -0
  166. package/dist/local-log-routing.d.ts +19 -0
  167. package/dist/local-log-routing.d.ts.map +1 -0
  168. package/dist/local-log-routing.js +67 -0
  169. package/dist/local-log-routing.js.map +1 -0
  170. package/dist/local-manage-tool-result.d.ts +8 -0
  171. package/dist/local-manage-tool-result.d.ts.map +1 -0
  172. package/dist/local-manage-tool-result.js +10 -0
  173. package/dist/local-manage-tool-result.js.map +1 -0
  174. package/dist/local-server-cursor.d.ts +34 -0
  175. package/dist/local-server-cursor.d.ts.map +1 -0
  176. package/dist/local-server-cursor.js +151 -0
  177. package/dist/local-server-cursor.js.map +1 -0
  178. package/dist/log-audit.d.ts.map +1 -0
  179. package/dist/log-audit.js +194 -3
  180. package/dist/log-audit.js.map +1 -0
  181. package/dist/log-stream.d.ts +35 -18
  182. package/dist/log-stream.d.ts.map +1 -0
  183. package/dist/log-stream.js +1270 -12
  184. package/dist/log-stream.js.map +1 -0
  185. package/dist/model-presets.d.ts.map +1 -0
  186. package/dist/model-presets.js +19 -1
  187. package/dist/model-presets.js.map +1 -0
  188. package/dist/name-validator.d.ts.map +1 -0
  189. package/dist/name-validator.js +22 -1
  190. package/dist/name-validator.js.map +1 -0
  191. package/dist/opencode-drone.d.ts.map +1 -0
  192. package/dist/opencode-drone.js +438 -4
  193. package/dist/opencode-drone.js.map +1 -0
  194. package/dist/opencode-plugin.d.ts +1 -1
  195. package/dist/opencode-plugin.d.ts.map +1 -0
  196. package/dist/opencode-plugin.js +29 -4
  197. package/dist/opencode-plugin.js.map +1 -0
  198. package/dist/parse-assimilate-args.d.ts +1 -1
  199. package/dist/parse-assimilate-args.d.ts.map +1 -0
  200. package/dist/parse-assimilate-args.js +125 -1
  201. package/dist/parse-assimilate-args.js.map +1 -0
  202. package/dist/parse-launch-all-args.d.ts.map +1 -0
  203. package/dist/parse-launch-all-args.js +70 -1
  204. package/dist/parse-launch-all-args.js.map +1 -0
  205. package/dist/postinstall-banner.d.ts.map +1 -0
  206. package/dist/postinstall-banner.js +27 -2
  207. package/dist/postinstall-banner.js.map +1 -0
  208. package/dist/postinstall.d.ts.map +1 -0
  209. package/dist/postinstall.js +32 -5
  210. package/dist/postinstall.js.map +1 -0
  211. package/dist/readiness-probe.d.ts.map +1 -0
  212. package/dist/readiness-probe.js +9 -1
  213. package/dist/readiness-probe.js.map +1 -0
  214. package/dist/regen-format.d.ts.map +1 -0
  215. package/dist/regen-format.js +545 -13
  216. package/dist/regen-format.js.map +1 -0
  217. package/dist/regen.d.ts.map +1 -0
  218. package/dist/regen.js +141 -5
  219. package/dist/regen.js.map +1 -0
  220. package/dist/remote-client.d.ts +88 -173
  221. package/dist/remote-client.d.ts.map +1 -0
  222. package/dist/remote-client.js +997 -1
  223. package/dist/remote-client.js.map +1 -0
  224. package/dist/reset-local-seat-cmd.d.ts +50 -0
  225. package/dist/reset-local-seat-cmd.d.ts.map +1 -0
  226. package/dist/reset-local-seat-cmd.js +169 -0
  227. package/dist/reset-local-seat-cmd.js.map +1 -0
  228. package/dist/role-match.d.ts.map +1 -0
  229. package/dist/role-match.js +23 -1
  230. package/dist/role-match.js.map +1 -0
  231. package/dist/role-resolver.d.ts.map +1 -0
  232. package/dist/role-resolver.js +60 -1
  233. package/dist/role-resolver.js.map +1 -0
  234. package/dist/roster-render.d.ts.map +1 -0
  235. package/dist/roster-render.js +121 -3
  236. package/dist/roster-render.js.map +1 -0
  237. package/dist/seat-probe.d.ts +32 -13
  238. package/dist/seat-probe.d.ts.map +1 -0
  239. package/dist/seat-probe.js +78 -1
  240. package/dist/seat-probe.js.map +1 -0
  241. package/dist/seat-store.d.ts +76 -0
  242. package/dist/seat-store.d.ts.map +1 -0
  243. package/dist/seat-store.js +309 -0
  244. package/dist/seat-store.js.map +1 -0
  245. package/dist/seats.d.ts +375 -0
  246. package/dist/seats.d.ts.map +1 -0
  247. package/dist/seats.js +670 -0
  248. package/dist/seats.js.map +1 -0
  249. package/dist/self-path.d.ts +27 -0
  250. package/dist/self-path.d.ts.map +1 -0
  251. package/dist/self-path.js +43 -0
  252. package/dist/self-path.js.map +1 -0
  253. package/dist/server-endpoint.d.ts +9 -0
  254. package/dist/server-endpoint.d.ts.map +1 -0
  255. package/dist/server-endpoint.js +38 -0
  256. package/dist/server-endpoint.js.map +1 -0
  257. package/dist/server-errors.d.ts +50 -0
  258. package/dist/server-errors.d.ts.map +1 -0
  259. package/dist/server-errors.js +79 -0
  260. package/dist/server-errors.js.map +1 -0
  261. package/dist/server-handshake.d.ts +197 -0
  262. package/dist/server-handshake.d.ts.map +1 -0
  263. package/dist/server-handshake.js +533 -0
  264. package/dist/server-handshake.js.map +1 -0
  265. package/dist/server-response.d.ts +3 -0
  266. package/dist/server-response.d.ts.map +1 -0
  267. package/dist/server-response.js +67 -0
  268. package/dist/server-response.js.map +1 -0
  269. package/dist/server-trust.d.ts +14 -0
  270. package/dist/server-trust.d.ts.map +1 -0
  271. package/dist/server-trust.js +225 -0
  272. package/dist/server-trust.js.map +1 -0
  273. package/dist/session-continuity.d.ts +33 -0
  274. package/dist/session-continuity.d.ts.map +1 -0
  275. package/dist/session-continuity.js +220 -0
  276. package/dist/session-continuity.js.map +1 -0
  277. package/dist/setup-confirm.d.ts +3 -3
  278. package/dist/setup-confirm.d.ts.map +1 -0
  279. package/dist/setup-confirm.js +126 -2
  280. package/dist/setup-confirm.js.map +1 -0
  281. package/dist/setup.d.ts +5 -3
  282. package/dist/setup.d.ts.map +1 -0
  283. package/dist/setup.js +169 -46
  284. package/dist/setup.js.map +1 -0
  285. package/dist/shell-escape.d.ts.map +1 -0
  286. package/dist/shell-escape.js +22 -1
  287. package/dist/shell-escape.js.map +1 -0
  288. package/dist/spawn.d.ts +2 -2
  289. package/dist/spawn.d.ts.map +1 -0
  290. package/dist/spawn.js +29 -10
  291. package/dist/spawn.js.map +1 -0
  292. package/dist/startup-services.d.ts +0 -1
  293. package/dist/startup-services.d.ts.map +1 -0
  294. package/dist/startup-services.js +26 -1
  295. package/dist/startup-services.js.map +1 -0
  296. package/dist/stream-owner.d.ts +6 -2
  297. package/dist/stream-owner.d.ts.map +1 -0
  298. package/dist/stream-owner.js +547 -2
  299. package/dist/stream-owner.js.map +1 -0
  300. package/dist/stream-status.d.ts +1 -1
  301. package/dist/stream-status.d.ts.map +1 -0
  302. package/dist/stream-status.js +268 -3
  303. package/dist/stream-status.js.map +1 -0
  304. package/dist/sync-roles-render.d.ts.map +1 -0
  305. package/dist/sync-roles-render.js +118 -3
  306. package/dist/sync-roles-render.js.map +1 -0
  307. package/dist/sync.d.ts +1 -1
  308. package/dist/sync.d.ts.map +1 -0
  309. package/dist/sync.js +286 -22
  310. package/dist/sync.js.map +1 -0
  311. package/dist/terminal-title.d.ts.map +1 -0
  312. package/dist/terminal-title.js +68 -1
  313. package/dist/terminal-title.js.map +1 -0
  314. package/dist/token-store.d.ts +17 -111
  315. package/dist/token-store.d.ts.map +1 -0
  316. package/dist/token-store.js +81 -1
  317. package/dist/token-store.js.map +1 -0
  318. package/dist/tool-manifest.d.ts +4 -8
  319. package/dist/tool-manifest.d.ts.map +1 -0
  320. package/dist/tool-manifest.js +554 -1
  321. package/dist/tool-manifest.js.map +1 -0
  322. package/dist/tool-scope.d.ts +8 -12
  323. package/dist/tool-scope.d.ts.map +1 -0
  324. package/dist/tool-scope.js +97 -1
  325. package/dist/tool-scope.js.map +1 -0
  326. package/dist/types.d.ts +1 -5
  327. package/dist/types.d.ts.map +1 -0
  328. package/dist/types.js +5 -0
  329. package/dist/types.js.map +1 -0
  330. package/dist/unknown-subcommand.d.ts +1 -1
  331. package/dist/unknown-subcommand.d.ts.map +1 -0
  332. package/dist/unknown-subcommand.js +37 -1
  333. package/dist/unknown-subcommand.js.map +1 -0
  334. package/dist/version.d.ts +1 -1
  335. package/dist/version.d.ts.map +1 -0
  336. package/dist/version.js +78 -2
  337. package/dist/version.js.map +1 -0
  338. package/dist/working-repo.d.ts.map +1 -0
  339. package/dist/working-repo.js +81 -1
  340. package/dist/working-repo.js.map +1 -0
  341. package/dist/worktree-lifecycle.d.ts.map +1 -0
  342. package/dist/worktree-lifecycle.js +205 -2
  343. package/dist/worktree-lifecycle.js.map +1 -0
  344. package/docs/EXTRACTION_PROVENANCE.md +42 -0
  345. package/docs/LOCAL_SERVER.md +103 -0
  346. package/docs/RELEASING.md +129 -0
  347. package/package.json +52 -34
  348. package/src/agent-runtime.ts +69 -0
  349. package/src/assimilate-cmd.ts +1864 -0
  350. package/src/assimilate-deps.ts +444 -0
  351. package/src/assimilate-guard.ts +84 -0
  352. package/src/assimilate-welcome.ts +39 -0
  353. package/src/auth-env.ts +21 -0
  354. package/src/backends/launch-all-pastelist.ts +18 -0
  355. package/src/backends/launch-all-tmux.ts +75 -0
  356. package/src/backends/launch-all-windows.ts +110 -0
  357. package/src/bare-launch-menu.ts +148 -0
  358. package/src/claude-launch-args.ts +35 -0
  359. package/src/claude.ts +561 -0
  360. package/src/cleanup-cmd.ts +581 -0
  361. package/src/clear-rewake-core.ts +34 -0
  362. package/src/clear-rewake.ts +18 -0
  363. package/src/cli-help.ts +116 -0
  364. package/src/cli-platform.ts +127 -0
  365. package/src/cli-tool-approval.ts +716 -0
  366. package/src/codex-app-server.ts +238 -0
  367. package/src/codex-app-wake.ts +524 -0
  368. package/src/codex-launch.ts +140 -0
  369. package/src/codex-remote.ts +500 -0
  370. package/src/codex-wake-resolve.ts +155 -0
  371. package/src/config-utils.ts +811 -0
  372. package/src/config.ts +595 -0
  373. package/src/console-prefix.ts +99 -0
  374. package/src/cube-name.ts +69 -0
  375. package/src/cubes.ts +583 -0
  376. package/src/debug.ts +73 -0
  377. package/src/direct-log.ts +9 -0
  378. package/src/docs-sections.ts +129 -0
  379. package/src/drone-lifecycle.ts +62 -0
  380. package/src/drone-management.ts +162 -0
  381. package/src/ensure-mcp-config.ts +54 -0
  382. package/src/evict-drone.ts +82 -0
  383. package/src/gc-orphan-inboxes.ts +229 -0
  384. package/src/inbox-monitor.ts +1005 -0
  385. package/src/index.ts +1201 -0
  386. package/src/launch-all-cmd.ts +450 -0
  387. package/src/launch-all-command.ts +30 -0
  388. package/src/launch-all-deps.ts +188 -0
  389. package/src/launch-all-discovery.ts +118 -0
  390. package/src/launch-all-locks.ts +74 -0
  391. package/src/launch-gate.ts +80 -0
  392. package/src/lifecycle-log-guard.ts +144 -0
  393. package/src/list-roles-render.ts +52 -0
  394. package/src/local-log-routing.ts +106 -0
  395. package/src/local-manage-tool-result.ts +10 -0
  396. package/src/local-server-cursor.ts +188 -0
  397. package/src/log-audit.ts +207 -0
  398. package/src/log-stream.ts +1567 -0
  399. package/src/model-presets.ts +22 -0
  400. package/src/name-validator.ts +23 -0
  401. package/src/opencode-drone.ts +528 -0
  402. package/src/opencode-plugin.ts +38 -0
  403. package/src/parse-assimilate-args.ts +125 -0
  404. package/src/parse-launch-all-args.ts +100 -0
  405. package/src/postinstall-banner.ts +37 -0
  406. package/src/postinstall.ts +36 -0
  407. package/src/readiness-probe.ts +12 -0
  408. package/src/regen-format.ts +651 -0
  409. package/src/regen.ts +150 -0
  410. package/src/remote-client.ts +1457 -0
  411. package/src/reset-local-seat-cmd.ts +227 -0
  412. package/src/role-match.ts +29 -0
  413. package/src/role-resolver.ts +93 -0
  414. package/src/roster-render.ts +196 -0
  415. package/src/seat-probe.ts +115 -0
  416. package/src/seat-store.ts +333 -0
  417. package/src/seats.ts +911 -0
  418. package/src/self-path.ts +51 -0
  419. package/src/server-endpoint.ts +38 -0
  420. package/src/server-errors.ts +95 -0
  421. package/src/server-handshake.ts +816 -0
  422. package/src/server-response.ts +76 -0
  423. package/src/server-trust.ts +245 -0
  424. package/src/session-continuity.ts +280 -0
  425. package/src/setup-confirm.ts +171 -0
  426. package/src/setup.ts +186 -0
  427. package/src/shell-escape.ts +22 -0
  428. package/src/spawn.ts +31 -0
  429. package/src/startup-services.ts +36 -0
  430. package/src/stream-owner.ts +686 -0
  431. package/src/stream-status.ts +337 -0
  432. package/src/sync-roles-render.ts +163 -0
  433. package/src/sync.ts +363 -0
  434. package/src/terminal-title.ts +76 -0
  435. package/src/token-store.ts +102 -0
  436. package/src/tool-manifest.ts +610 -0
  437. package/src/tool-scope.ts +110 -0
  438. package/src/types.ts +5 -0
  439. package/src/unknown-subcommand.ts +35 -0
  440. package/src/version.ts +82 -0
  441. package/src/working-repo.ts +99 -0
  442. package/src/worktree-lifecycle.ts +254 -0
  443. package/dist/auth-recovery.d.ts +0 -33
  444. package/dist/auth-recovery.js +0 -1
  445. package/dist/auth.d.ts +0 -103
  446. package/dist/auth.js +0 -39
  447. package/dist/device-auth.d.ts +0 -75
  448. package/dist/device-auth.js +0 -1
  449. package/dist/drone-address.d.ts +0 -26
  450. package/dist/drone-address.js +0 -1
  451. package/dist/get-started.d.ts +0 -20
  452. package/dist/get-started.js +0 -2
  453. package/dist/health-beat.d.ts +0 -134
  454. package/dist/health-beat.js +0 -1
  455. package/dist/role-section.d.ts +0 -110
  456. package/dist/role-section.js +0 -8
  457. package/dist/setup-action.d.ts +0 -20
  458. package/dist/setup-action.js +0 -1
  459. package/dist/stale-version-check.d.ts +0 -40
  460. package/dist/stale-version-check.js +0 -1
  461. package/dist/subscription-retry.d.ts +0 -40
  462. package/dist/subscription-retry.js +0 -1
  463. package/dist/templates.d.ts +0 -107
  464. package/dist/templates.js +0 -359
  465. package/dist/token-crypto.d.ts +0 -50
  466. package/dist/token-crypto.js +0 -1
@@ -0,0 +1,610 @@
1
+ /**
2
+ * gh#docs-site — SOURCE-OF-TRUTH tool manifest.
3
+ *
4
+ * The single canonical list of borg_* MCP tool definitions. The runtime and
5
+ * documentation consumers use the same pure-data list.
6
+ *
7
+ * PURE DATA — no imports, no side effects — so documentation builds do not pull
8
+ * in the client's MCP runtime dependencies.
9
+ */
10
+ export interface ToolManifestEntry {
11
+ name: string;
12
+ description: string;
13
+ inputSchema: {
14
+ type: string;
15
+ properties: Record<string, any>;
16
+ required?: string[];
17
+ oneOf?: Array<{ required: string[] }>;
18
+ };
19
+ }
20
+
21
+ export const TOOL_MANIFEST: ToolManifestEntry[] = [
22
+ {
23
+ name: 'borg_regen',
24
+ description:
25
+ "Refresh your context as a Drone. Returns the active cube's directive, " +
26
+ "your role's detailed playbook, the drone roster, and recent activity log entries — " +
27
+ 'everything you need to be oriented. Call on session start, and again before each new ' +
28
+ 'task to stay in sync with the cube. Returns "not connected" if no active cube; use ' +
29
+ 'borg_assimilate first in that case. ' +
30
+ 'Optional `since` (entry-id UUID or ISO-8601 timestamp) trims the recent-log section ' +
31
+ 'to entries strictly after the anchor — pass your last-seen entry id to skip ' +
32
+ 'already-processed history on each refresh. If you know the current session model, pass ' +
33
+ 'optional `model` to self-report it as advisory metadata; unrecognized model strings are accepted.',
34
+ inputSchema: {
35
+ type: 'object',
36
+ properties: {
37
+ since: {
38
+ type: 'string',
39
+ description:
40
+ 'Optional cursor. Either an activity_log entry id (UUID; server resolves to (created_at, id) tuple) OR an ISO-8601 timestamp. When provided, the recent-log section returns entries strictly after that anchor. Non-existent UUID falls back to default recent window.',
41
+ },
42
+ mode: {
43
+ type: 'string',
44
+ enum: ['full', 'lite'],
45
+ description:
46
+ 'Optional output mode. Use full at session start and after context compaction. Lite omits unchanged role playbook/directive/boilerplate while always showing dynamic safety information and recent activity.',
47
+ },
48
+ model: {
49
+ type: 'string',
50
+ maxLength: 256,
51
+ description:
52
+ 'Optional advisory self-report of the model running this agent session. Use the model identifier you know from session context; the server does not infer or validate it against an allowlist.',
53
+ },
54
+ },
55
+ required: [],
56
+ },
57
+ },
58
+ {
59
+ name: 'borg_assimilate',
60
+ description:
61
+ "RE-ATTACH this session to the drone seat already saved for this worktree (gh#780: " +
62
+ "this tool never creates seats). Provide the cube's name; on a match it returns the " +
63
+ "cube directive, your role's instructions, and recent activity for the EXISTING seat. " +
64
+ 'To create a seat or switch cubes, run `borg assimilate` in a terminal instead.',
65
+ inputSchema: {
66
+ type: 'object',
67
+ properties: {
68
+ cube_name: {
69
+ type: 'string',
70
+ description: 'The cube to connect to',
71
+ },
72
+ },
73
+ required: ['cube_name'],
74
+ },
75
+ },
76
+ {
77
+ name: 'borg_cube',
78
+ description:
79
+ "Read the active Cube's directive and the registry of all roles in it " +
80
+ "(each role's name + short description). Use to remind yourself of cube-wide context.",
81
+ inputSchema: {
82
+ type: 'object',
83
+ properties: {},
84
+ required: [],
85
+ },
86
+ },
87
+ {
88
+ name: 'borg_role',
89
+ description:
90
+ "Read a role's detailed playbook. With no arguments, returns YOUR " +
91
+ 'assigned role. Pass `role` (a role name, case-insensitive, or role id) ' +
92
+ 'to read any other role in the cube — role playbooks are cube-internal ' +
93
+ 'shared context, readable by any drone.',
94
+ inputSchema: {
95
+ type: 'object',
96
+ properties: {
97
+ role: {
98
+ type: 'string',
99
+ description:
100
+ 'Optional. A role name (case-insensitive) or role id. Omit to read your own role.',
101
+ },
102
+ },
103
+ required: [],
104
+ },
105
+ },
106
+ {
107
+ name: 'borg_version',
108
+ description:
109
+ 'Returns the installed borgmcp client version. Use to verify which version is running in this MCP session.',
110
+ inputSchema: {
111
+ type: 'object',
112
+ properties: {},
113
+ required: [],
114
+ },
115
+ },
116
+ {
117
+ name: 'borg_playbook',
118
+ description:
119
+ 'Load the full operating-playbook chapter — the detailed disciplines, rationale, and examples behind the rule-spine in your regen (verification discipline v1/v2/v3, concrete source-of-truth surfaces, four-surface propagation). This detail is kept OUT of the regen bootstrap to keep it light; fetch it ONCE per session when doing review/verify-class work. Static text — do NOT re-fetch on every wake.',
120
+ inputSchema: {
121
+ type: 'object',
122
+ properties: {},
123
+ required: [],
124
+ },
125
+ },
126
+ {
127
+ name: 'borg_docs',
128
+ description:
129
+ 'Look up the Borg MCP documentation. Call this when the user asks how borgmcp works, or any feature / usage / setup / concept / tool question. Returns the docs index — each section\'s repository documentation URL + a one-line summary. Pass `topic` (e.g. "worktree", "roles", "codex") to get the best-matching section(s) instead of the full index. Then WebFetch the returned URL to read the page — borg_docs returns the index only, it does not fetch the page for you.',
130
+ inputSchema: {
131
+ type: 'object',
132
+ properties: {
133
+ topic: {
134
+ type: 'string',
135
+ description:
136
+ 'Optional search topic — returns the best-matching docs section(s) instead of the full index.',
137
+ },
138
+ },
139
+ required: [],
140
+ },
141
+ },
142
+ {
143
+ name: 'borg_whoami',
144
+ description:
145
+ 'Returns your identity in the current cube: cube name, drone label, and role name. Use to confirm which cube/role/drone you are.',
146
+ inputSchema: {
147
+ type: 'object',
148
+ properties: {},
149
+ required: [],
150
+ },
151
+ },
152
+ {
153
+ name: 'borg_role-rationale',
154
+ description:
155
+ "Fetch an on-demand rationale/case-study section for a role playbook. " +
156
+ "Pass a role name/id and a plain-label section key to read the rationale without expanding every regen.",
157
+ inputSchema: {
158
+ type: 'object',
159
+ properties: {
160
+ role: {
161
+ type: 'string',
162
+ description: 'Role name or role id to fetch rationale for, e.g. Builder.',
163
+ },
164
+ section: {
165
+ type: 'string',
166
+ description: 'Plain-label role section key, e.g. Workflow rationale.',
167
+ },
168
+ },
169
+ required: ['role', 'section'],
170
+ },
171
+ },
172
+ {
173
+ name: 'borg_roster',
174
+ description:
175
+ "List all currently connected drones in your cube, with each drone's label, role, and last-seen time. Optional `since` argument adds a sender-side liveness column — pass either an activity_log entry id (e.g., from a dispatch you posted) or an ISO-8601 timestamp; each drone is marked `awake` if they've posted a log entry after that point, otherwise `stale-since-X`. Useful for confirming a dispatch reached its named recipients (catches the silent-wake-path-failure class where SSE delivered but the drone's /loop never woke).",
176
+ inputSchema: {
177
+ type: 'object',
178
+ properties: {
179
+ since: {
180
+ type: 'string',
181
+ description:
182
+ 'Optional liveness reference point. Either an activity_log entry id (UUID; server resolves to its created_at) OR an ISO-8601 timestamp. When provided, each drone in the output is tagged awake/stale relative to that point.',
183
+ },
184
+ },
185
+ required: [],
186
+ },
187
+ },
188
+ {
189
+ name: 'borg_stream-status',
190
+ description:
191
+ "Diagnostic probe of the local SSE log-stream consumer: returns `connected`, `lastContentEventAt`, `lastWireActivityAt`, `lastHeartbeatAt`, `lastPersistedEventId`, `reconnectAttempts`, plus a wake-path check that flags if SSE is attached but no inbox-Monitor is watching the file (the silent failure where `/loop` never wakes on incoming entries). Read-only in-process state; does NOT re-open the stream. Use when troubleshooting wake-ups or verifying the stream is alive.",
192
+ inputSchema: {
193
+ type: 'object',
194
+ properties: {},
195
+ required: [],
196
+ },
197
+ },
198
+ {
199
+ name: 'borg_read-log',
200
+ description:
201
+ "Read entries from the cube's activity log. Each entry is tagged " +
202
+ "with the drone that wrote it and that drone's role. For wake triage, prefer " +
203
+ '`unread_only=true` with a modest limit and drain until `has_more=false`; ' +
204
+ 'this reads oldest-unread-first from your server cursor and ' +
205
+ 'advances the watermark so bursts are not skipped. Optional `since` is a strict-after ' +
206
+ 'cursor for explicit bounded reads only; do not use it with the same timestamp as a ' +
207
+ 'notification preview because it can skip the boundary entry.',
208
+ inputSchema: {
209
+ type: 'object',
210
+ properties: {
211
+ since: {
212
+ type: 'string',
213
+ description:
214
+ 'Optional strict-after cursor for explicit bounded reads. Either an activity_log entry id (UUID; server resolves to (created_at, id) tuple for deterministic tie-break) OR an ISO-8601 timestamp. Do not use for routine wake triage; prefer unread_only.',
215
+ },
216
+ limit: {
217
+ type: 'number',
218
+ description: 'max entries to return (1-500)',
219
+ },
220
+ unread_only: {
221
+ type: 'boolean',
222
+ description:
223
+ 'When true, read only entries posted after this drone last called read-log, oldest-unread-first. Server advances the watermark to the newest returned entry on every call; if has_more=true, call again until has_more=false.',
224
+ },
225
+ },
226
+ },
227
+ },
228
+ {
229
+ name: 'borg_ack',
230
+ description:
231
+ 'Mark a log entry as explicitly acknowledged (kind="ack", default), or claim advisory ownership of a review gate before starting (kind="claim"). Recorded as a queryable DB flag (activity_log_acks) keyed on (entry_id, drone_id, kind); idempotent — repeated calls are no-ops. ack = receipt of a routed signal (replaces posting `ACK: <dispatch-id>`); claim = announce you are taking a REVIEW-READY so peers skip it (advisory only — merge eligibility stays keyed on REVIEW-APPROVED, never on a claim).',
232
+ inputSchema: {
233
+ type: 'object',
234
+ required: ['entry_id'],
235
+ properties: {
236
+ entry_id: {
237
+ type: 'string',
238
+ description: 'UUID of the log entry to acknowledge.',
239
+ },
240
+ kind: {
241
+ type: 'string',
242
+ enum: ['ack', 'claim'],
243
+ description:
244
+ 'Coordination kind. "ack" (default) = receipt. "claim" = advisory ownership of a review gate on a REVIEW-READY entry (wakes the gate audience; renders stale if you go silent past the wake-path SLA).',
245
+ },
246
+ },
247
+ },
248
+ },
249
+ {
250
+ name: 'borg_decide',
251
+ description:
252
+ 'Record a RATIFIED cube decision in the durable decision registry (gh#740) so drones cite it by topic instead of restating from memory. Coordinator/Queen are workflow-eligible to ratify, but their labels grant no server permission; the selected local client must have a live cube-manage grant. Recording IS the ratification act; a decision is not ratified until it is in the registry. Topic-keyed: recording a new decision on an existing topic supersedes the prior (one active per topic). Surfaces in borg_regen + borg_decisions.',
253
+ inputSchema: {
254
+ type: 'object',
255
+ required: ['topic', 'decision'],
256
+ properties: {
257
+ topic: {
258
+ type: 'string',
259
+ description: 'Stable topic key for cite-by-topic + supersession (e.g. "pricing-model"). Max 120 chars.',
260
+ },
261
+ decision: {
262
+ type: 'string',
263
+ description: 'The ratified decision text. Max 2000 chars.',
264
+ },
265
+ rationale: {
266
+ type: 'string',
267
+ description: 'Optional why. Max 2000 chars.',
268
+ },
269
+ },
270
+ },
271
+ },
272
+ {
273
+ name: 'borg_decisions',
274
+ description:
275
+ 'List the active ratified decisions for the cube (gh#740) — the source of truth to CITE instead of restating a decision from memory. Any member may read. Pass `topic` to fetch one topic\'s active decision; omit for all active decisions.',
276
+ inputSchema: {
277
+ type: 'object',
278
+ properties: {
279
+ topic: {
280
+ type: 'string',
281
+ description: 'Optional topic key to fetch that topic\'s active decision.',
282
+ },
283
+ },
284
+ },
285
+ },
286
+ {
287
+ name: 'borg_remove-decision',
288
+ description:
289
+ 'Remove one active ratified decision from the cube registry by topic or decision id. Coordinator/Queen are workflow-eligible, but their labels grant no server permission; the selected local client must have a live cube-manage grant. The decision stops appearing in borg_decisions and borg_regen while its audit record is retained.',
290
+ inputSchema: {
291
+ type: 'object',
292
+ oneOf: [{ required: ['topic'] }, { required: ['decision_id'] }],
293
+ properties: {
294
+ topic: {
295
+ type: 'string',
296
+ description: 'Topic of the active decision to remove. Provide exactly one selector.',
297
+ },
298
+ decision_id: {
299
+ type: 'string',
300
+ format: 'uuid',
301
+ description: 'Id of the active decision to remove. Provide exactly one selector.',
302
+ },
303
+ },
304
+ },
305
+ },
306
+ {
307
+ name: 'borg_log',
308
+ description:
309
+ 'Append a message to the cube\'s activity log. By default entries broadcast to all drones. When a cube declares a message taxonomy, borg_log applies class-based smart defaults: prefix-matched directed classes route to their default recipients unless you pass `to:`, `class:`, or explicit visibility. Pass `to: [...]` to direct by exact drone label, drone id, the 8-hex short-uuid (the `id:` token shown in roster/read-log — a drone_id prefix that is STABLE across label renumber), role name, or role slug.',
310
+ inputSchema: {
311
+ type: 'object',
312
+ properties: {
313
+ message: { type: 'string', description: 'The log message (max 10KB).' },
314
+ to: {
315
+ type: 'array',
316
+ items: { type: 'string' },
317
+ description:
318
+ 'Optional direct-message recipients by exact drone label, drone id, the 8-hex short-uuid (`id:` token from roster/read-log; stable across label renumber), role name, or role slug (resolves to all drones in that role). Omit to let class-based routing or broadcast defaults apply.',
319
+ },
320
+ class: {
321
+ type: 'string',
322
+ description:
323
+ 'Optional declared message class. Overrides prefix auto-classification when the cube declares a message taxonomy.',
324
+ },
325
+ visibility: {
326
+ type: 'string',
327
+ enum: ['broadcast', 'direct'],
328
+ description: 'Optional explicit visibility. Overrides class-based routing defaults.',
329
+ },
330
+ },
331
+ required: ['message'],
332
+ },
333
+ },
334
+ {
335
+ name: 'borg_list-cubes',
336
+ description: 'List every cube readable by this local client\'s live grants. Returns id, name, cube_directive, and timestamps for each. Useful before assimilate to see what\'s available, or as a starting point for an authorized management action.',
337
+ inputSchema: { type: 'object', properties: {} },
338
+ },
339
+ {
340
+ name: 'borg_create-cube',
341
+ description:
342
+ 'Create a new cube. The server seeds a default "Drone" role atomically so the cube is assimilatable immediately. ' +
343
+ 'Pass an optional `template` name to apply a richer role set instead (see borg_list-templates / borg_apply-template).',
344
+ inputSchema: {
345
+ type: 'object',
346
+ properties: {
347
+ name: {
348
+ type: 'string',
349
+ description: 'Cube name (lowercase letters, digits, hyphens; max 64 chars).',
350
+ pattern: '^[a-z0-9-]+$',
351
+ maxLength: 64,
352
+ },
353
+ cube_directive: { type: 'string', description: 'Markdown text every drone in this cube will see in regen. Anything project-specific.' },
354
+ template: {
355
+ type: 'string',
356
+ description: 'Optional template name to apply after cube creation (e.g. "software-dev"). Roles are merged by name; the default Drone role gets overwritten by the template if a same-named role is in the template.',
357
+ },
358
+ },
359
+ required: ['name', 'cube_directive'],
360
+ },
361
+ },
362
+ {
363
+ name: 'borg_update-cube',
364
+ description: 'Update a cube\'s name, cube_directive, and/or message_taxonomy. Pass only what changes.',
365
+ inputSchema: {
366
+ type: 'object',
367
+ properties: {
368
+ cube_id: { type: 'string', description: 'UUID of the cube to update.' },
369
+ name: {
370
+ type: 'string',
371
+ description: 'New name (optional). Lowercase letters, digits, hyphens; max 64 chars.',
372
+ pattern: '^[a-z0-9-]+$',
373
+ maxLength: 64,
374
+ },
375
+ cube_directive: { type: 'string', description: 'New cube directive markdown (optional).' },
376
+ message_taxonomy: {
377
+ type: 'array',
378
+ description: 'New message-class taxonomy (optional). REPLACES the whole taxonomy; the worker re-validates the full array (non-overlapping prefixes, unique class names, directed classes need default_to). Pass [] to clear. To change ONE class without resending the whole array, use borg_patch-taxonomy-class instead. In default_to, pass @human-seat to route to drones in the cube human-seat role(s); literal role names/slugs/labels still work. Optional lifecycle tags mark dispatch/completion classes for stuck-dispatch detection.',
379
+ items: {
380
+ type: 'object',
381
+ properties: {
382
+ class: { type: 'string', description: 'Unique class name.' },
383
+ prefixes: { type: 'array', items: { type: 'string' }, description: 'Message prefixes routed by this class.' },
384
+ routing: { type: 'string', enum: ['broadcast', 'directed'], description: 'Routing mode.' },
385
+ default_to: { type: 'array', items: { type: 'string' }, description: 'Default recipients (role name/slug/label, or @human-seat) for a directed class.' },
386
+ lifecycle: { type: 'string', enum: ['dispatch', 'completion'], description: 'Optional lifecycle marker for stuck-dispatch detection.' },
387
+ },
388
+ },
389
+ },
390
+ },
391
+ required: ['cube_id'],
392
+ },
393
+ },
394
+ {
395
+ name: 'borg_patch-taxonomy-class',
396
+ description:
397
+ "Patch ONE message-class in a cube's message_taxonomy without resending the whole taxonomy (avoids clobbering). action=add|replace|remove (replace/remove match name case-insensitively). The full taxonomy is re-validated after the patch (non-overlapping prefixes, unique names, directed classes need default_to) — a patch that breaks a rule against an untouched class is rejected. In default_to, @human-seat routes to the cube's human-seat role(s); literal names/slugs/labels also work. Optional lifecycle tags mark dispatch/completion classes for stuck-dispatch detection.",
398
+ inputSchema: {
399
+ type: 'object',
400
+ properties: {
401
+ cube_id: { type: 'string', description: 'UUID of the cube to patch.' },
402
+ action: { type: 'string', enum: ['add', 'replace', 'remove'], description: 'add / replace / remove a single class.' },
403
+ class_def: {
404
+ type: 'object',
405
+ description: 'The class definition (for add/replace). Shape: { class, prefixes?, routing: "broadcast"|"directed", default_to?, lifecycle? }.',
406
+ properties: {
407
+ class: { type: 'string', description: 'Unique class name.' },
408
+ prefixes: { type: 'array', items: { type: 'string' }, description: 'Message prefixes routed by this class.' },
409
+ routing: { type: 'string', enum: ['broadcast', 'directed'], description: 'Routing mode.' },
410
+ default_to: { type: 'array', items: { type: 'string' }, description: 'Default recipients (required for directed classes): role name/slug/label, or @human-seat.' },
411
+ lifecycle: { type: 'string', enum: ['dispatch', 'completion'], description: 'Optional lifecycle marker for stuck-dispatch detection.' },
412
+ },
413
+ required: ['class', 'routing'],
414
+ },
415
+ class: { type: 'string', description: 'For remove only: the name of the class to drop (case-insensitive).' },
416
+ },
417
+ required: ['cube_id', 'action'],
418
+ },
419
+ },
420
+ {
421
+ name: 'borg_delete-cube',
422
+ description: 'Delete a cube and all its roles, drones, and log entries. Irreversible — confirm with the user before invoking unless the cube is clearly disposable.',
423
+ inputSchema: {
424
+ type: 'object',
425
+ properties: {
426
+ cube_id: { type: 'string', description: 'UUID of the cube to delete.' },
427
+ },
428
+ required: ['cube_id'],
429
+ },
430
+ },
431
+ {
432
+ name: 'borg_create-role',
433
+ description: 'Create a role inside a cube. The detailed_description is the role\'s playbook — only drones assigned to this role see it. Setting is_default=true demotes any existing default; a cube has exactly one default role at a time.',
434
+ inputSchema: {
435
+ type: 'object',
436
+ properties: {
437
+ cube_id: { type: 'string', description: 'UUID of the cube this role belongs to.' },
438
+ name: { type: 'string', description: 'Role name (e.g. "Builder", "Reviewer").' },
439
+ short_description: { type: 'string', description: 'One-line summary, shown to every drone in the cube.' },
440
+ detailed_description: { type: 'string', description: 'Full playbook for drones in this role — workflow, conventions, log signals to post.' },
441
+ is_default: { type: 'boolean', description: 'If true, new drones assimilating into this cube are assigned this role. Demotes the previous default.' },
442
+ is_mandatory: { type: 'boolean', description: 'If true, role-less assimilate fills this unoccupied non-queen role before ordinary worker roles. A mandatory human-seat role is therefore selected first until occupied.' },
443
+ is_human_seat: { type: 'boolean', description: 'If true, this role represents the cube\'s human-occupied seat (where the human Queen sits directly). The class-hierarchy guard in reassign-drone allows promotion FROM a human-seat role TO the platform Queen role; promotion from non-human-seat roles is rejected.' },
444
+ can_broadcast: { type: 'boolean', description: 'If true, drones in this role may post broadcast log entries when strict broadcast gating is enabled.' },
445
+ receives_all_direct: { type: 'boolean', description: 'If true, drones in this role can see direct log entries as observer/audit recipients.' },
446
+ },
447
+ required: ['cube_id', 'name', 'short_description', 'detailed_description'],
448
+ },
449
+ },
450
+ {
451
+ name: 'borg_update-role',
452
+ description: 'Update a role. Pass only the fields that change. Promoting to is_default demotes the previous default in the same cube.',
453
+ inputSchema: {
454
+ type: 'object',
455
+ properties: {
456
+ role_id: { type: 'string', description: 'UUID of the role to update.' },
457
+ name: { type: 'string', description: 'New role name (optional).' },
458
+ short_description: { type: 'string', description: 'New short description (optional).' },
459
+ detailed_description: { type: 'string', description: 'New detailed playbook (optional).' },
460
+ is_default: { type: 'boolean', description: 'Set true to make this the cube\'s default role (optional).' },
461
+ is_mandatory: { type: 'boolean', description: 'Set true/false to prioritize this unoccupied non-queen role during role-less assimilate.' },
462
+ is_human_seat: { type: 'boolean', description: 'Set true/false to mark/unmark this as the cube\'s human-occupied seat (the elevation source for the platform Queen role).' },
463
+ can_broadcast: { type: 'boolean', description: 'Set true/false to allow or deny broadcast log entries when strict broadcast gating is enabled.' },
464
+ receives_all_direct: { type: 'boolean', description: 'Set true/false to grant or remove observer visibility into direct log entries.' },
465
+ },
466
+ required: ['role_id'],
467
+ },
468
+ },
469
+ {
470
+ name: 'borg_patch-role-section',
471
+ description:
472
+ "Surgically patch ONE named section of a role's detailed_description, leaving the rest of the field byte-identical. Sections are delimited by plain-label lines (e.g. `Workflow:`, `Project conventions:`) — NOT markdown headings; text before the first label is the preamble. Use this instead of borg_update-role when changing a single section so you don't have to resend (and risk clobbering) the whole playbook. action=replace overwrites a section's body; action=insert adds a new section (optionally after a named one, else appended); action=delete removes a section.",
473
+ inputSchema: {
474
+ type: 'object',
475
+ properties: {
476
+ role_id: { type: 'string', description: 'UUID of the role to patch.' },
477
+ action: { type: 'string', enum: ['replace', 'insert', 'delete'], description: 'replace / insert / delete a single section.' },
478
+ heading: { type: 'string', description: 'The section label WITHOUT the trailing colon (e.g. "Workflow"). Matched case-insensitively.' },
479
+ body: { type: 'string', description: 'New text BELOW the heading (for replace/insert). Omit for delete.' },
480
+ after: { type: 'string', description: 'For insert only: place the new section after the section with this heading. Omit/null to append at the end.' },
481
+ },
482
+ required: ['role_id', 'action', 'heading'],
483
+ },
484
+ },
485
+ {
486
+ name: 'borg_delete-role',
487
+ description: 'Delete a role. Refuses if any drone is still assigned — reassign them with borg_reassign-drone or remove them with borg_evict-drone first.',
488
+ inputSchema: {
489
+ type: 'object',
490
+ properties: {
491
+ role_id: { type: 'string', description: 'UUID of the role to delete.' },
492
+ },
493
+ required: ['role_id'],
494
+ },
495
+ },
496
+ {
497
+ name: 'borg_reassign-drone',
498
+ description:
499
+ 'Reassign a drone within the current cube using the selected local client\'s cube-management grant. Returns server-derived drone, cube, and role readback. Coordinator and Queen are workflow labels, not server permissions.',
500
+ inputSchema: {
501
+ type: 'object',
502
+ properties: {
503
+ drone_id: { type: 'string', description: 'UUID of the drone to reassign.' },
504
+ role_id: { type: 'string', description: 'UUID of the target role. Must belong to the same cube as the drone.' },
505
+ },
506
+ required: ['drone_id', 'role_id'],
507
+ },
508
+ },
509
+ {
510
+ name: 'borg_evict-drone',
511
+ description:
512
+ 'Remove a drone using the selected local client\'s cube-management grant. The seat credential is revoked, project files remain, and activity history keeps the removed seat\'s attribution. Accepts drone_id for the current cube or label with cube_id.',
513
+ inputSchema: {
514
+ type: 'object',
515
+ properties: {
516
+ drone_id: { type: 'string', description: 'UUID of the drone to evict. Provide this OR (label + cube_id).' },
517
+ label: { type: 'string', description: 'Drone label to evict, e.g. "two-of-seventeen-builder". Requires cube_id and cannot be combined with drone_id.' },
518
+ cube_id: { type: 'string', description: 'UUID of the cube the labelled drone belongs to. Required when evicting by label.' },
519
+ },
520
+ },
521
+ },
522
+ {
523
+ name: 'borg_list-drones',
524
+ description:
525
+ 'List every drone in a cube when this local client has a live read, write, or manage grant. Returns id, label, role_id, agent_kind, last_seen, advisory reported model, working repository, and wake_path_alert_class. Role labels affect workflow only and grant no server permission.',
526
+ inputSchema: {
527
+ type: 'object',
528
+ properties: {
529
+ cube_id: { type: 'string', description: 'UUID of the cube whose drones to list.' },
530
+ },
531
+ required: ['cube_id'],
532
+ },
533
+ },
534
+ {
535
+ name: 'borg_list-roles',
536
+ description:
537
+ 'List every role in a cube when this local client has a live read, write, or manage grant. Returns id, name, short_description, is_default, is_mandatory, is_human_seat, can_broadcast, receives_all_direct, and role_class. Role labels affect workflow only and grant no server permission.',
538
+ inputSchema: {
539
+ type: 'object',
540
+ properties: {
541
+ cube_id: { type: 'string', description: 'UUID of the cube whose roles to list.' },
542
+ },
543
+ required: ['cube_id'],
544
+ },
545
+ },
546
+ {
547
+ name: 'borg_list-templates',
548
+ description: 'List available cube templates that can be applied via borg_apply-template or passed to borg_create-cube.',
549
+ inputSchema: { type: 'object', properties: {} },
550
+ },
551
+ {
552
+ name: 'borg_apply-template',
553
+ description:
554
+ 'Apply a named template to an existing cube, NON-CLOBBERINGLY. Roles are merged by name: new roles are created; existing template-named roles get template sections/classes the cube LACKS auto-applied, but EVOLVED (conflicting) text is preserved, never overwritten. Use this to retrofit an existing cube with a richer role set (e.g. add Coordinator/Reviewer/UX Expert). To review + selectively accept conflicting fragments, use borg_sync-roles (which surfaces each conflict + takes per-fragment accept decisions).',
555
+ inputSchema: {
556
+ type: 'object',
557
+ properties: {
558
+ cube_id: { type: 'string', description: 'UUID of the cube to apply the template to.' },
559
+ template_name: { type: 'string', description: 'Template to apply (see borg_list-templates).' },
560
+ },
561
+ required: ['cube_id', 'template_name'],
562
+ },
563
+ },
564
+ {
565
+ name: 'borg_sync-roles',
566
+ description:
567
+ 'Non-clobbering sync of a cube\'s roles + message_taxonomy against the built-in template. Dry-run (default) classifies each fragment (role-text section, short_description, role flags, taxonomy class) as ADD (cube lacks it — safe auto-apply), UNCHANGED, or CONFLICT (cube has EVOLVED text). On apply, ADDs auto-apply; CONFLICTs apply ONLY via an explicit `decisions` accept (keyed on the dry-run fragment key, e.g. `role:Builder:section:Workflow`); unspecified conflicts default to reject — evolved text is NEVER silently overwritten. Custom roles untouched.',
568
+ inputSchema: {
569
+ type: 'object',
570
+ properties: {
571
+ cube_id: { type: 'string', description: 'UUID of the cube to sync.' },
572
+ template_name: { type: 'string', description: 'Template to sync against (default: software-dev).' },
573
+ apply: { type: 'boolean', description: 'If true, commit (auto-apply ADDs + accepted conflicts). If false (default), dry-run only — classify + surface conflicts.' },
574
+ decisions: {
575
+ type: 'object',
576
+ description: 'Per-conflict accept/reject map, keyed on the fragment key from the dry-run (e.g. {"role:Builder:section:Workflow":"accept"}). Unspecified conflicts default to "reject" (keep the cube version).',
577
+ additionalProperties: { type: 'string', enum: ['accept', 'reject'] },
578
+ },
579
+ },
580
+ required: ['cube_id'],
581
+ },
582
+ },
583
+ // gh#899: dispatcher escape hatch — ALWAYS native in every role's surface
584
+ // so deferred (filtered-out) tools are never lost. Routes through the
585
+ // identical CallTool→handler→userId+Zod path (no weaker entry); this is
586
+ // a UX/context optimization, NOT an authorization boundary.
587
+ {
588
+ name: 'borg_tool',
589
+ description: 'Dispatcher: invoke ANY borg tool by name, including tools not pre-loaded in your role-scoped surface. Pass {"name":"<borg_tool>","arguments":{...}}. Routes through the identical auth + validation path as a direct call. Call borg_describe-tool first to learn a deferred tool\'s arguments.',
590
+ inputSchema: {
591
+ type: 'object',
592
+ properties: {
593
+ name: { type: 'string', description: 'The borg tool to invoke, e.g. "borg_evict-drone".' },
594
+ arguments: { type: 'object', description: 'The arguments object for that tool (same shape as a direct call).' },
595
+ },
596
+ required: ['name'],
597
+ },
598
+ },
599
+ {
600
+ name: 'borg_describe-tool',
601
+ description: 'Return the description + input schema for any borg tool by name — including deferred tools not pre-loaded in your surface. Schema-only; never executes the tool. Pair with borg_tool to invoke a deferred tool.',
602
+ inputSchema: {
603
+ type: 'object',
604
+ properties: {
605
+ name: { type: 'string', description: 'The borg tool to describe.' },
606
+ },
607
+ required: ['name'],
608
+ },
609
+ },
610
+ ];