@north-light/crouter 0.3.318 → 0.3.319

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 (1303) hide show
  1. package/README.md +0 -3
  2. package/dist/api/client.js +2 -912
  3. package/dist/api/dto/attach.js +0 -13
  4. package/dist/api/dto/bash-jobs.js +1 -9
  5. package/dist/api/dto/broker-ops.js +0 -6
  6. package/dist/api/dto/broker.js +0 -20
  7. package/dist/api/dto/canvas.js +0 -2
  8. package/dist/api/dto/chat-inventory.js +0 -11
  9. package/dist/api/dto/common.js +1 -15
  10. package/dist/api/dto/config.js +0 -3
  11. package/dist/api/dto/crons.js +1 -10
  12. package/dist/api/dto/files.js +0 -7
  13. package/dist/api/dto/focus.js +0 -10
  14. package/dist/api/dto/health.js +0 -2
  15. package/dist/api/dto/human-requests.js +0 -4
  16. package/dist/api/dto/human.js +0 -4
  17. package/dist/api/dto/inbox.js +0 -4
  18. package/dist/api/dto/lifecycle.js +0 -3
  19. package/dist/api/dto/mail.js +0 -1
  20. package/dist/api/dto/memory.js +0 -6
  21. package/dist/api/dto/messages.js +0 -2
  22. package/dist/api/dto/model-config.js +0 -1
  23. package/dist/api/dto/modelauth.js +0 -4
  24. package/dist/api/dto/node-outcomes.js +0 -2
  25. package/dist/api/dto/nodes.js +0 -3
  26. package/dist/api/dto/profiles.js +1 -4
  27. package/dist/api/dto/recovery.js +0 -1
  28. package/dist/api/dto/reports.js +0 -2
  29. package/dist/api/dto/review-comments.js +0 -5
  30. package/dist/api/dto/reviews.js +0 -5
  31. package/dist/api/dto/subscriptions.js +0 -2
  32. package/dist/api/dto/worktree.js +0 -6
  33. package/dist/api/errors.js +1 -40
  34. package/dist/api/index.js +1 -33
  35. package/dist/api/plugin-manifest-schema.js +0 -23
  36. package/dist/api/routes.js +1 -147
  37. package/dist/build-root.js +1 -198
  38. package/dist/cli.js +3 -99
  39. package/dist/clients/attach/ansi-cells.js +1 -137
  40. package/dist/clients/attach/chrome/bash-jobs.js +1 -31
  41. package/dist/clients/attach/chrome/canvas-panels.js +1 -194
  42. package/dist/clients/attach/chrome/completion-bell.js +1 -89
  43. package/dist/clients/attach/chrome/cron-wait.js +1 -34
  44. package/dist/clients/attach/chrome/git-info.js +2 -44
  45. package/dist/clients/attach/chrome/header.js +1 -30
  46. package/dist/clients/attach/chrome/inbox-strip.js +1 -199
  47. package/dist/clients/attach/chrome/recap.js +1 -19
  48. package/dist/clients/attach/chrome/review-wait.js +1 -22
  49. package/dist/clients/attach/chrome/roster.js +4 -275
  50. package/dist/clients/attach/chrome/status-line.js +1 -117
  51. package/dist/clients/attach/chrome/ticket-panel.js +1 -280
  52. package/dist/clients/attach/chrome/widgets.js +1 -51
  53. package/dist/clients/attach/command.js +1 -107
  54. package/dist/clients/attach/config.js +1 -274
  55. package/dist/clients/attach/input/capabilities.js +1 -104
  56. package/dist/clients/attach/input/clipboard-image.js +3 -220
  57. package/dist/clients/attach/input/completion-frecency.js +1 -141
  58. package/dist/clients/attach/input/controller.js +7 -377
  59. package/dist/clients/attach/input/overlay-owner.js +1 -199
  60. package/dist/clients/attach/input/ref-autocomplete.js +2 -176
  61. package/dist/clients/attach/input/titled-editor.js +4 -859
  62. package/dist/clients/attach/overlays/auth.js +2 -271
  63. package/dist/clients/attach/overlays/dialogs.js +2 -102
  64. package/dist/clients/attach/overlays/file-review.js +2 -128
  65. package/dist/clients/attach/overlays/graph.js +1 -661
  66. package/dist/clients/attach/overlays/help.js +1 -211
  67. package/dist/clients/attach/overlays/mcp.js +1 -302
  68. package/dist/clients/attach/overlays/pickers.js +1 -163
  69. package/dist/clients/attach/render/activity-slot.js +1 -13
  70. package/dist/clients/attach/render/assistant-message.js +1 -56
  71. package/dist/clients/attach/render/card-presentation.js +5 -218
  72. package/dist/clients/attach/render/chat-view.js +5 -1708
  73. package/dist/clients/attach/render/condensed-history.js +1 -60
  74. package/dist/clients/attach/render/context-message.js +1 -63
  75. package/dist/clients/attach/render/crtr-output.js +17 -905
  76. package/dist/clients/attach/render/diagram.js +7 -111
  77. package/dist/clients/attach/render/edit-diff.js +5 -304
  78. package/dist/clients/attach/render/glyph-codepoints.js +1 -42
  79. package/dist/clients/attach/render/group-activity.js +2 -263
  80. package/dist/clients/attach/render/group-recap.js +1 -152
  81. package/dist/clients/attach/render/markdown-source.js +5 -266
  82. package/dist/clients/attach/render/measured-container.js +1 -322
  83. package/dist/clients/attach/render/page-block.js +1 -183
  84. package/dist/clients/attach/render/scroll-animation.js +1 -80
  85. package/dist/clients/attach/render/tool-calls.js +3 -361
  86. package/dist/clients/attach/render/transcript-copy.js +2 -81
  87. package/dist/clients/attach/render/transcript-search.js +1 -152
  88. package/dist/clients/attach/render/viewport.js +1 -184
  89. package/dist/clients/attach/session/banner.js +1 -29
  90. package/dist/clients/attach/session/bindings.js +1 -71
  91. package/dist/clients/attach/session/chrome-refresh.js +1 -94
  92. package/dist/clients/attach/session/connection.js +1 -186
  93. package/dist/clients/attach/session/context.js +0 -16
  94. package/dist/clients/attach/session/editor-frame.js +1 -142
  95. package/dist/clients/attach/session/editor-inventory.js +6 -160
  96. package/dist/clients/attach/session/file-links.js +1 -68
  97. package/dist/clients/attach/session/focus-events.js +1 -12
  98. package/dist/clients/attach/session/frame.js +1 -214
  99. package/dist/clients/attach/session/frames.js +1 -188
  100. package/dist/clients/attach/session/identity.js +1 -26
  101. package/dist/clients/attach/session/input-wiring.js +1 -140
  102. package/dist/clients/attach/session/invariant.js +1 -15
  103. package/dist/clients/attach/session/keys.js +1 -77
  104. package/dist/clients/attach/session/layout.js +1 -59
  105. package/dist/clients/attach/session/mouse.js +1 -78
  106. package/dist/clients/attach/session/pane-focus.js +1 -42
  107. package/dist/clients/attach/session/pane-tag.js +1 -112
  108. package/dist/clients/attach/session/pi-assets.js +1 -24
  109. package/dist/clients/attach/session/pi-oauth-flows.js +1 -21
  110. package/dist/clients/attach/session/profile-files.js +1 -228
  111. package/dist/clients/attach/session/reconnect.js +1 -175
  112. package/dist/clients/attach/session/selection.js +3 -108
  113. package/dist/clients/attach/session/state-sync.js +1 -67
  114. package/dist/clients/attach/session/surface-frame.js +1 -73
  115. package/dist/clients/attach/session/surface-host.js +1 -255
  116. package/dist/clients/attach/session/teardown.js +5 -94
  117. package/dist/clients/attach/session/transcript-search.js +3 -151
  118. package/dist/clients/attach/session/whip-achievements.js +2 -145
  119. package/dist/clients/attach/session/whip.js +1 -362
  120. package/dist/clients/attach/slash/dispatch.js +1 -706
  121. package/dist/clients/attach/slash/prompt-preview.js +1 -121
  122. package/dist/clients/attach/viewer.js +441 -441
  123. package/dist/clients/conversation/projection.js +1 -324
  124. package/dist/clients/conversation/submit.js +1 -51
  125. package/dist/clients/inbox/controller.js +1 -701
  126. package/dist/clients/inbox/dto-adapt.js +1 -93
  127. package/dist/clients/inbox/layout.js +1 -9
  128. package/dist/clients/inbox/page-adapter.js +1 -55
  129. package/dist/clients/inbox/resolve.js +1 -35
  130. package/dist/clients/inbox/review/anchors.js +1 -89
  131. package/dist/clients/inbox/review/comments-client.js +1 -98
  132. package/dist/clients/inbox/review/companion-pane.js +1 -82
  133. package/dist/clients/inbox/review/document-surface.js +2 -1188
  134. package/dist/clients/inbox/review/frame.js +1 -216
  135. package/dist/clients/inbox/review/keys.js +1 -123
  136. package/dist/clients/inbox/review/launch.js +1 -151
  137. package/dist/clients/inbox/review/live-source.js +1 -160
  138. package/dist/clients/inbox/review/nvim.js +1 -44
  139. package/dist/clients/inbox/review/remap.js +1 -157
  140. package/dist/clients/inbox/review/review-client.js +1 -123
  141. package/dist/clients/inbox/review/roundtrip.js +3 -36
  142. package/dist/clients/inbox/review/state.js +4 -315
  143. package/dist/clients/inbox/review-adapter.js +1 -43
  144. package/dist/clients/inbox/surface.js +1 -152
  145. package/dist/clients/inbox/tui/ansi.js +3 -321
  146. package/dist/clients/inbox/tui/input.js +5 -392
  147. package/dist/clients/inbox/tui/keys.js +1 -104
  148. package/dist/clients/inbox/tui/page-body.js +1 -66
  149. package/dist/clients/inbox/tui/panel.js +1 -84
  150. package/dist/clients/inbox/tui/render.js +2 -368
  151. package/dist/clients/inbox/tui/slots.js +3 -134
  152. package/dist/clients/inbox/tui/types.js +0 -1
  153. package/dist/clients/inbox/tui.js +1 -86
  154. package/dist/clients/surfaces/host.js +0 -1
  155. package/dist/commands/api-client.js +4 -290
  156. package/dist/commands/attention.js +1 -215
  157. package/dist/commands/canvas-browse.js +1 -70
  158. package/dist/commands/canvas-config.js +2 -192
  159. package/dist/commands/canvas-history/grep.js +7 -85
  160. package/dist/commands/canvas-history/read.js +3 -50
  161. package/dist/commands/canvas-history/search.js +10 -99
  162. package/dist/commands/canvas-history/shared.js +1 -139
  163. package/dist/commands/canvas-history/stats.js +6 -68
  164. package/dist/commands/canvas-history.js +1 -32
  165. package/dist/commands/canvas-issue.js +14 -149
  166. package/dist/commands/canvas-prune.js +1 -108
  167. package/dist/commands/canvas-roster.js +1 -69
  168. package/dist/commands/canvas-snapshot.js +1 -34
  169. package/dist/commands/canvas-use.js +1 -61
  170. package/dist/commands/canvas.js +1 -49
  171. package/dist/commands/chord.js +1 -241
  172. package/dist/commands/cron.js +11 -534
  173. package/dist/commands/dashboard.js +1 -85
  174. package/dist/commands/human/components.js +3 -77
  175. package/dist/commands/human/feedback.js +1 -112
  176. package/dist/commands/human/prompts.js +1 -331
  177. package/dist/commands/human/queue.js +1 -191
  178. package/dist/commands/human/request.js +1 -266
  179. package/dist/commands/human/review.js +1 -288
  180. package/dist/commands/human/shared.js +1 -67
  181. package/dist/commands/human.js +4 -60
  182. package/dist/commands/memory/delete.js +1 -100
  183. package/dist/commands/memory/edit.js +21 -219
  184. package/dist/commands/memory/find.js +2 -244
  185. package/dist/commands/memory/history.js +5 -199
  186. package/dist/commands/memory/lint.js +1 -107
  187. package/dist/commands/memory/list.js +1 -142
  188. package/dist/commands/memory/move.js +1 -223
  189. package/dist/commands/memory/origin.js +1 -130
  190. package/dist/commands/memory/read.js +6 -232
  191. package/dist/commands/memory/shared.js +12 -802
  192. package/dist/commands/memory/write.js +13 -235
  193. package/dist/commands/memory.js +1 -30
  194. package/dist/commands/node/bash.js +5 -245
  195. package/dist/commands/node/create.js +3 -332
  196. package/dist/commands/node/inspect.js +12 -300
  197. package/dist/commands/node/lifecycle.js +2 -453
  198. package/dist/commands/node/message.js +1 -161
  199. package/dist/commands/node/outcome.js +4 -134
  200. package/dist/commands/node/pyramid.js +2 -79
  201. package/dist/commands/node/subscription.js +1 -78
  202. package/dist/commands/node/wait.js +7 -163
  203. package/dist/commands/node-context.js +2 -159
  204. package/dist/commands/node-inspect-artifacts.js +8 -109
  205. package/dist/commands/node-lifecycle-revive.js +1 -217
  206. package/dist/commands/node-snapshot.js +1 -37
  207. package/dist/commands/node-transcript.js +1 -62
  208. package/dist/commands/node-worktree.js +1 -138
  209. package/dist/commands/node.js +1 -29
  210. package/dist/commands/pkg/browse/actions.js +1 -198
  211. package/dist/commands/pkg/browse/catalog.js +1 -466
  212. package/dist/commands/pkg/browse/command-view.js +1 -191
  213. package/dist/commands/pkg/browse/detail-panel.js +1 -402
  214. package/dist/commands/pkg/browse/doc-view.js +1 -89
  215. package/dist/commands/pkg/browse/list-panel.js +2 -168
  216. package/dist/commands/pkg/browse/model.js +1 -36
  217. package/dist/commands/pkg/browse/shell.js +1 -640
  218. package/dist/commands/pkg/browse.js +1 -27
  219. package/dist/commands/pkg/market-inspect.js +1 -141
  220. package/dist/commands/pkg/market-manage.js +1 -327
  221. package/dist/commands/pkg/market.js +1 -14
  222. package/dist/commands/pkg/plugin-inspect.js +1 -168
  223. package/dist/commands/pkg/plugin-manage.js +17 -1109
  224. package/dist/commands/pkg/plugin.js +1 -14
  225. package/dist/commands/pkg/shared.js +1 -62
  226. package/dist/commands/pkg.js +1 -21
  227. package/dist/commands/profile/default.js +1 -139
  228. package/dist/commands/profile/delete.js +1 -66
  229. package/dist/commands/profile/env.js +3 -188
  230. package/dist/commands/profile/kind.js +2 -35
  231. package/dist/commands/profile/list.js +1 -43
  232. package/dist/commands/profile/meta.js +1 -67
  233. package/dist/commands/profile/new.js +1 -115
  234. package/dist/commands/profile/pause.js +1 -59
  235. package/dist/commands/profile/project.js +1 -113
  236. package/dist/commands/profile/rename.js +1 -38
  237. package/dist/commands/profile/show.js +1 -52
  238. package/dist/commands/profile.js +1 -35
  239. package/dist/commands/push.js +9 -265
  240. package/dist/commands/revive.js +10 -181
  241. package/dist/commands/surface/node/cycle.js +1 -83
  242. package/dist/commands/surface/node/focus.js +1 -81
  243. package/dist/commands/surface/node/id.js +1 -38
  244. package/dist/commands/surface/node/pin.js +1 -42
  245. package/dist/commands/surface/node/placement.js +1 -134
  246. package/dist/commands/surface-edit.js +1 -157
  247. package/dist/commands/surface-inbox.js +1 -98
  248. package/dist/commands/surface-inspect.js +1 -39
  249. package/dist/commands/surface-node.js +1 -19
  250. package/dist/commands/surface-reload.js +2 -134
  251. package/dist/commands/surface-tmux-spread.js +1 -214
  252. package/dist/commands/surface.js +1 -28
  253. package/dist/commands/sys/branch.js +1 -19
  254. package/dist/commands/sys/config.js +1 -353
  255. package/dist/commands/sys/context/admin/actions.js +2 -246
  256. package/dist/commands/sys/context/admin/detail-panel.js +1 -247
  257. package/dist/commands/sys/context/admin/docs-panel.js +1 -191
  258. package/dist/commands/sys/context/admin/list-view.js +1 -183
  259. package/dist/commands/sys/context/admin/model.js +1 -229
  260. package/dist/commands/sys/context/admin/rail-panel.js +1 -227
  261. package/dist/commands/sys/context/admin/read-view.js +2 -194
  262. package/dist/commands/sys/context/admin/shell.js +1 -910
  263. package/dist/commands/sys/context/admin.js +2 -126
  264. package/dist/commands/sys/context/doc.js +3 -197
  265. package/dist/commands/sys/context/prompt-review.js +11 -291
  266. package/dist/commands/sys/context/resolve.js +10 -489
  267. package/dist/commands/sys/context/sysprompt.js +5 -96
  268. package/dist/commands/sys/context.js +1 -20
  269. package/dist/commands/sys/daemon.js +1 -313
  270. package/dist/commands/sys/doctor.js +1 -617
  271. package/dist/commands/sys/feedback.js +7 -228
  272. package/dist/commands/sys/logs.js +3 -129
  273. package/dist/commands/sys/migrate.js +1 -94
  274. package/dist/commands/sys/panels/broker-limits-panel.js +2 -110
  275. package/dist/commands/sys/panels/dependencies-panel.js +1 -80
  276. package/dist/commands/sys/panels/keybindings-panel.js +1 -703
  277. package/dist/commands/sys/panels/models-panel.js +1 -1133
  278. package/dist/commands/sys/panels/plugins-panel.js +1 -80
  279. package/dist/commands/sys/panels/prefs-panel.js +1 -85
  280. package/dist/commands/sys/panels/profiles-panel.js +1 -601
  281. package/dist/commands/sys/panels/provider-panel.js +1 -538
  282. package/dist/commands/sys/settings-shell.js +1 -400
  283. package/dist/commands/sys/settings.js +1 -46
  284. package/dist/commands/sys/setup-core.js +6 -579
  285. package/dist/commands/sys/setup-settings-runner.js +1 -16
  286. package/dist/commands/sys/setup-wizard.js +1 -279
  287. package/dist/commands/sys/setup.js +1 -34
  288. package/dist/commands/sys/shared.js +1 -81
  289. package/dist/commands/sys/support/prepare.js +3 -239
  290. package/dist/commands/sys/support/submit.js +6 -524
  291. package/dist/commands/sys/support.js +1 -18
  292. package/dist/commands/sys/sync-deps.js +15 -498
  293. package/dist/commands/sys/sync-project-guidance.js +4 -481
  294. package/dist/commands/sys/sync-shared.js +1 -49
  295. package/dist/commands/sys/sync-skills.js +2 -311
  296. package/dist/commands/sys/sync.js +1 -18
  297. package/dist/commands/sys/update.js +1 -147
  298. package/dist/commands/sys/worktrees.js +5 -53
  299. package/dist/commands/sys.js +1 -18
  300. package/dist/core/activity-signal.js +2 -38
  301. package/dist/core/asset-root.js +1 -18
  302. package/dist/core/auth-file.js +2 -179
  303. package/dist/core/auth-interaction.js +3 -94
  304. package/dist/core/auto-update.js +4 -94
  305. package/dist/core/bash-guard.js +11 -393
  306. package/dist/core/bash-jobs.js +7 -411
  307. package/dist/core/bootstrap.js +2 -53
  308. package/dist/core/broker-client/client.js +1 -184
  309. package/dist/core/broker-client/index.js +1 -13
  310. package/dist/core/broker-client/transport-relay.js +1 -157
  311. package/dist/core/broker-client/transport-socket.js +1 -179
  312. package/dist/core/broker-client/transport.js +1 -26
  313. package/dist/core/canvas/attention.js +1 -47
  314. package/dist/core/canvas/boot-id.js +1 -26
  315. package/dist/core/canvas/boot.js +1 -186
  316. package/dist/core/canvas/browse/app.js +3 -919
  317. package/dist/core/canvas/browse/model.js +1 -477
  318. package/dist/core/canvas/browse/pins.js +1 -29
  319. package/dist/core/canvas/browse/render.js +3 -1055
  320. package/dist/core/canvas/canvas.js +15 -922
  321. package/dist/core/canvas/crons.js +11 -481
  322. package/dist/core/canvas/daemon-owner.js +2 -146
  323. package/dist/core/canvas/db.js +2 -100
  324. package/dist/core/canvas/deliveries.js +22 -283
  325. package/dist/core/canvas/delivery-contract.js +1 -8
  326. package/dist/core/canvas/executions.js +1 -68
  327. package/dist/core/canvas/extensions.js +1 -83
  328. package/dist/core/canvas/focuses.js +1 -77
  329. package/dist/core/canvas/history.js +24 -860
  330. package/dist/core/canvas/index.js +1 -15
  331. package/dist/core/canvas/install-id.js +1 -84
  332. package/dist/core/canvas/labels.js +1 -43
  333. package/dist/core/canvas/meta-file.js +1 -89
  334. package/dist/core/canvas/migrations.js +41 -1150
  335. package/dist/core/canvas/nav-model.js +1 -231
  336. package/dist/core/canvas/nav-render.js +1 -260
  337. package/dist/core/canvas/node-order.js +1 -37
  338. package/dist/core/canvas/node-recap.js +2 -67
  339. package/dist/core/canvas/node-sql-migration.js +2 -209
  340. package/dist/core/canvas/paths.js +1 -153
  341. package/dist/core/canvas/pid.js +4 -683
  342. package/dist/core/canvas/recovery.js +3 -565
  343. package/dist/core/canvas/remote-canvas-source.js +1 -288
  344. package/dist/core/canvas/remote-transport.js +1 -57
  345. package/dist/core/canvas/render-source.js +10 -635
  346. package/dist/core/canvas/sessions.js +1 -78
  347. package/dist/core/canvas/source.js +1 -47
  348. package/dist/core/canvas/status-glyph.js +1 -132
  349. package/dist/core/canvas/telemetry.js +1 -35
  350. package/dist/core/canvas/types.js +1 -6
  351. package/dist/core/canvas/waits.js +4 -68
  352. package/dist/core/canvas/worktrees.js +1 -93
  353. package/dist/core/clipboard-text.js +1 -57
  354. package/dist/core/command-hooks/artifact.js +1 -145
  355. package/dist/core/command-hooks/catalog.js +1 -38
  356. package/dist/core/command-hooks/compose.js +1 -99
  357. package/dist/core/command-hooks/discovery.js +1 -228
  358. package/dist/core/command-hooks/help.js +1 -18
  359. package/dist/core/command-hooks/index.js +1 -7
  360. package/dist/core/command-hooks/lifecycle-catalog.js +1 -9
  361. package/dist/core/command-hooks/lifecycle-create.js +1 -51
  362. package/dist/core/command-hooks/report.js +1 -28
  363. package/dist/core/command-hooks/schema.js +1 -157
  364. package/dist/core/command-hooks/transport/exec-invoke.js +1 -276
  365. package/dist/core/command-hooks/transport/exec-lifecycle.js +1 -211
  366. package/dist/core/command-manifests/manifest.js +1 -324
  367. package/dist/core/command-manifests/registry.js +1 -118
  368. package/dist/core/command-manifests/schema.js +1 -736
  369. package/dist/core/command-plugins/bundle.js +1 -261
  370. package/dist/core/command-plugins/compose.js +1 -65
  371. package/dist/core/command-plugins/discovery.js +1 -245
  372. package/dist/core/command-plugins/endpoint.js +1 -48
  373. package/dist/core/command-plugins/extensions.js +1 -166
  374. package/dist/core/command-plugins/help-addenda.js +1 -44
  375. package/dist/core/command-plugins/presence.js +1 -17
  376. package/dist/core/command-plugins/revalidate.js +2 -152
  377. package/dist/core/command-plugins/transport/exec-invoke.js +1 -215
  378. package/dist/core/command-plugins/transport/http-fetch.js +1 -68
  379. package/dist/core/command-plugins/transport/http-invoke.js +3 -546
  380. package/dist/core/command.js +10 -739
  381. package/dist/core/config.js +1 -1059
  382. package/dist/core/document-lines.js +3 -6
  383. package/dist/core/env-name.js +1 -9
  384. package/dist/core/errors.js +1 -52
  385. package/dist/core/events/emit.js +1 -17
  386. package/dist/core/events/envelope.js +1 -84
  387. package/dist/core/events/errors.js +1 -69
  388. package/dist/core/events/index.js +1 -4
  389. package/dist/core/events/operation-id.js +1 -24
  390. package/dist/core/events/read.js +1 -623
  391. package/dist/core/events/serialize.js +1 -199
  392. package/dist/core/events/source.js +1 -31
  393. package/dist/core/events/types.js +1 -11
  394. package/dist/core/exclusive-lock.js +1 -197
  395. package/dist/core/fault-classifier.js +1 -96
  396. package/dist/core/feed/feed.js +7 -202
  397. package/dist/core/feed/inbox-migrate.js +3 -135
  398. package/dist/core/feed/inbox.js +10 -122
  399. package/dist/core/feed/messages.js +6 -212
  400. package/dist/core/frontmatter.js +1 -35
  401. package/dist/core/fs-utils.js +3 -202
  402. package/dist/core/git.js +2 -103
  403. package/dist/core/help.js +9 -310
  404. package/dist/core/host-exports/builtins.js +9 -68
  405. package/dist/core/host-exports/export.js +3 -124
  406. package/dist/core/human/action-binding.js +1 -40
  407. package/dist/core/human/answer-text.js +5 -100
  408. package/dist/core/human/answer.js +1 -119
  409. package/dist/core/human/claim.js +3 -67
  410. package/dist/core/human/completion.js +1 -27
  411. package/dist/core/human/component-docs.js +78 -272
  412. package/dist/core/human/convention.js +2 -82
  413. package/dist/core/human/feedback-companion.js +1 -106
  414. package/dist/core/human/feedback.js +1 -88
  415. package/dist/core/human/page-authoring.js +1 -19
  416. package/dist/core/human/page-catalog.js +1 -172
  417. package/dist/core/human/page-errors.js +1 -7
  418. package/dist/core/human/page-eval.js +1 -125
  419. package/dist/core/human/page-html-markdown.js +8 -260
  420. package/dist/core/human/page-markdown.js +17 -295
  421. package/dist/core/human/page-schema.js +1 -373
  422. package/dist/core/human/page-synth.js +8 -27
  423. package/dist/core/human/page.js +1 -198
  424. package/dist/core/human/requests.js +15 -466
  425. package/dist/core/human/review-schema.js +1 -34
  426. package/dist/core/human/root.js +1 -11
  427. package/dist/core/human/scan.js +1 -69
  428. package/dist/core/human/summary.js +1 -5
  429. package/dist/core/human/tickets.js +1 -171
  430. package/dist/core/human/types.js +0 -1
  431. package/dist/core/human/visible-paths.js +1 -77
  432. package/dist/core/human-actions.js +1 -101
  433. package/dist/core/inspector/chrome.js +1 -14
  434. package/dist/core/inspector/contract.js +0 -1
  435. package/dist/core/inspector/core.js +2 -295
  436. package/dist/core/inspector/host.js +4 -538
  437. package/dist/core/inspector/model.js +2 -226
  438. package/dist/core/inspector/text.js +6 -45
  439. package/dist/core/inspector/transport.js +1 -36
  440. package/dist/core/inspector/tui.js +2 -295
  441. package/dist/core/installed-plugins.js +1 -78
  442. package/dist/core/io.js +7 -356
  443. package/dist/core/keybindings/attach-control.js +1 -42
  444. package/dist/core/keybindings/background-bash.js +1 -33
  445. package/dist/core/keybindings/catalog.js +1 -256
  446. package/dist/core/keybindings/inbox.js +1 -25
  447. package/dist/core/keybindings/index.js +1 -7
  448. package/dist/core/keybindings/match.js +1 -127
  449. package/dist/core/keybindings/persistence.js +1 -49
  450. package/dist/core/keybindings/resolve.js +1 -348
  451. package/dist/core/keybindings/types.js +0 -1
  452. package/dist/core/locked-file.js +1 -118
  453. package/dist/core/log.js +3 -27
  454. package/dist/core/manifest-recovery.js +1 -72
  455. package/dist/core/manifest-stale.js +1 -39
  456. package/dist/core/manifest.js +1 -20
  457. package/dist/core/memory/doc-link-grammar.js +2 -109
  458. package/dist/core/memory/extensions.js +1 -221
  459. package/dist/core/memory/history.js +6 -268
  460. package/dist/core/memory/identity.js +1 -181
  461. package/dist/core/memory/inline-ref-grammar.js +1 -98
  462. package/dist/core/memory/inline-ref-guidance.js +2 -35
  463. package/dist/core/memory/inline-ref-inventory.js +1 -59
  464. package/dist/core/memory/lint.js +2 -671
  465. package/dist/core/memory/project-namespace.js +2 -85
  466. package/dist/core/memory/repository-association.js +1 -129
  467. package/dist/core/memory/tree.js +1 -93
  468. package/dist/core/memory-resolver.js +2 -611
  469. package/dist/core/model-config.js +1 -107
  470. package/dist/core/model-routes.js +1 -201
  471. package/dist/core/nested-stores.js +2 -166
  472. package/dist/core/output.js +7 -99
  473. package/dist/core/pagination.js +1 -88
  474. package/dist/core/plugin-swap-lock.js +1 -31
  475. package/dist/core/pool-credential-store.js +1 -116
  476. package/dist/core/predicate.js +1 -191
  477. package/dist/core/preview-registry.js +2 -411
  478. package/dist/core/preview-result-path.js +1 -26
  479. package/dist/core/profiles/default-binding.js +1 -24
  480. package/dist/core/profiles/deletion-reservation.js +1 -42
  481. package/dist/core/profiles/env-store.js +2 -162
  482. package/dist/core/profiles/fuzzy-match.js +1 -92
  483. package/dist/core/profiles/manifest.js +1 -574
  484. package/dist/core/profiles/select.js +35 -741
  485. package/dist/core/profiles/state-block.js +3 -17
  486. package/dist/core/provider-error-recognition.js +1 -74
  487. package/dist/core/provider-failure.js +1 -86
  488. package/dist/core/provider-management.js +1 -22
  489. package/dist/core/remote-canvas-target.js +1 -30
  490. package/dist/core/render.js +18 -138
  491. package/dist/core/resolver.js +1 -111
  492. package/dist/core/review/birth.js +1 -52
  493. package/dist/core/review/comments.js +5 -279
  494. package/dist/core/review/companion.js +1 -215
  495. package/dist/core/review/document.js +2 -138
  496. package/dist/core/review/project.js +1 -36
  497. package/dist/core/review/realize.js +1 -71
  498. package/dist/core/review/remap.js +4 -141
  499. package/dist/core/review/signal.js +1 -12
  500. package/dist/core/review/stage.js +1 -184
  501. package/dist/core/review/store.js +1 -168
  502. package/dist/core/review/types.js +1 -23
  503. package/dist/core/runtime/advertised-command-invocation.js +1 -233
  504. package/dist/core/runtime/auth-reload.js +1 -67
  505. package/dist/core/runtime/banner.js +1 -51
  506. package/dist/core/runtime/bearings-render.js +18 -250
  507. package/dist/core/runtime/bearings.js +7 -194
  508. package/dist/core/runtime/bin-contributions.js +2 -186
  509. package/dist/core/runtime/boot-root.js +1 -107
  510. package/dist/core/runtime/branded-host.js +2 -264
  511. package/dist/core/runtime/broker/auth-reload.js +1 -157
  512. package/dist/core/runtime/broker/client-registry.js +1 -179
  513. package/dist/core/runtime/broker/daemon-ops.js +1 -88
  514. package/dist/core/runtime/broker/engine-drive.js +1 -354
  515. package/dist/core/runtime/broker/engine-routing.js +1 -211
  516. package/dist/core/runtime/broker/event-projection.js +1 -193
  517. package/dist/core/runtime/broker/extension-abort.js +1 -36
  518. package/dist/core/runtime/broker/fault-retry.js +1 -588
  519. package/dist/core/runtime/broker/frame-client.js +1 -132
  520. package/dist/core/runtime/broker/frame-dispatch.js +1 -183
  521. package/dist/core/runtime/broker/frame-engine-control.js +1 -231
  522. package/dist/core/runtime/broker/frame-memory-refs.js +1 -41
  523. package/dist/core/runtime/broker/frame-model-query.js +1 -69
  524. package/dist/core/runtime/broker/frame-read.js +1 -116
  525. package/dist/core/runtime/broker/frame-replies.js +1 -64
  526. package/dist/core/runtime/broker/frame-session.js +4 -203
  527. package/dist/core/runtime/broker/held-deferred-inbox.js +1 -13
  528. package/dist/core/runtime/broker/inbox.js +13 -163
  529. package/dist/core/runtime/broker/node-named.js +1 -27
  530. package/dist/core/runtime/broker/read-ops.js +1 -171
  531. package/dist/core/runtime/broker/rebind.js +1 -318
  532. package/dist/core/runtime/broker/tool-groups.js +1 -246
  533. package/dist/core/runtime/broker/turn-admission.js +1 -31
  534. package/dist/core/runtime/broker/turn-ignition.js +1 -84
  535. package/dist/core/runtime/broker-cli.js +3 -81
  536. package/dist/core/runtime/broker-extension-render.js +5 -135
  537. package/dist/core/runtime/broker-inventory.js +1 -116
  538. package/dist/core/runtime/broker-persona-guidance.js +4 -154
  539. package/dist/core/runtime/broker-protocol.js +3 -152
  540. package/dist/core/runtime/broker-request.js +1 -85
  541. package/dist/core/runtime/broker-sdk.js +1 -129
  542. package/dist/core/runtime/broker.js +1 -1214
  543. package/dist/core/runtime/canvas-extensions.js +1 -96
  544. package/dist/core/runtime/chat-inventory-rows.js +1 -105
  545. package/dist/core/runtime/close.js +1 -265
  546. package/dist/core/runtime/command-expansion.js +9 -104
  547. package/dist/core/runtime/command-surface.js +1 -117
  548. package/dist/core/runtime/connectivity.js +1 -73
  549. package/dist/core/runtime/deliver-live.js +1 -88
  550. package/dist/core/runtime/fault-recovery.js +1 -83
  551. package/dist/core/runtime/fault.js +1 -17
  552. package/dist/core/runtime/fleet.js +1 -58
  553. package/dist/core/runtime/front-door-env.js +1 -16
  554. package/dist/core/runtime/front-door.js +7 -183
  555. package/dist/core/runtime/headless-pi.js +1 -161
  556. package/dist/core/runtime/host.js +1 -457
  557. package/dist/core/runtime/interactive-deliver.js +1 -51
  558. package/dist/core/runtime/invocation.js +0 -10
  559. package/dist/core/runtime/kickoff.js +30 -327
  560. package/dist/core/runtime/launch-config-worker.js +1 -12
  561. package/dist/core/runtime/launch-prompt.js +4 -13
  562. package/dist/core/runtime/launch-target.js +1 -55
  563. package/dist/core/runtime/launch.js +1 -483
  564. package/dist/core/runtime/lifecycle.js +2 -213
  565. package/dist/core/runtime/managed-provider-cooling.js +1 -62
  566. package/dist/core/runtime/memory.js +1 -17
  567. package/dist/core/runtime/model-registry.js +1 -13
  568. package/dist/core/runtime/model-selection.js +1 -135
  569. package/dist/core/runtime/model-swap.js +1 -86
  570. package/dist/core/runtime/naming.js +14 -298
  571. package/dist/core/runtime/nerd-font.js +2 -127
  572. package/dist/core/runtime/node-read.js +2 -386
  573. package/dist/core/runtime/nodes.js +1 -331
  574. package/dist/core/runtime/outcome-document.js +1 -97
  575. package/dist/core/runtime/package-health.js +4 -99
  576. package/dist/core/runtime/persona.js +2 -55
  577. package/dist/core/runtime/pi-cli.js +1 -65
  578. package/dist/core/runtime/pi-vendored.js +1 -66
  579. package/dist/core/runtime/placement-tmux.js +1 -81
  580. package/dist/core/runtime/placement.js +1 -386
  581. package/dist/core/runtime/promote.js +1 -174
  582. package/dist/core/runtime/prospective-inventory-cli.js +3 -61
  583. package/dist/core/runtime/prospective-inventory.js +2 -88
  584. package/dist/core/runtime/recap.js +27 -103
  585. package/dist/core/runtime/recycle.js +1 -190
  586. package/dist/core/runtime/reopen.js +1 -138
  587. package/dist/core/runtime/reset.js +1 -245
  588. package/dist/core/runtime/resume-root.js +10 -290
  589. package/dist/core/runtime/revive-all.js +1 -107
  590. package/dist/core/runtime/revive.js +4 -544
  591. package/dist/core/runtime/roadmap.js +4 -38
  592. package/dist/core/runtime/session-branch.js +1 -46
  593. package/dist/core/runtime/session-cycles.js +1 -110
  594. package/dist/core/runtime/session-list-cache.js +1 -406
  595. package/dist/core/runtime/session-visibility.js +1 -99
  596. package/dist/core/runtime/shell-expansion.js +9 -100
  597. package/dist/core/runtime/situational-context.js +2 -67
  598. package/dist/core/runtime/situational-live.js +1 -41
  599. package/dist/core/runtime/spawn-env.js +1 -255
  600. package/dist/core/runtime/spawn.js +3 -577
  601. package/dist/core/runtime/stamp/channel.js +1 -76
  602. package/dist/core/runtime/stamp/protocol.js +1 -113
  603. package/dist/core/runtime/stop-guard.js +7 -116
  604. package/dist/core/runtime/stop-signals.js +1 -46
  605. package/dist/core/runtime/stream-watchdog.js +1 -134
  606. package/dist/core/runtime/structured-output.js +4 -156
  607. package/dist/core/runtime/surface-bg.js +1 -85
  608. package/dist/core/runtime/tmux-bindings.js +4 -730
  609. package/dist/core/runtime/tmux-chrome.js +1 -5
  610. package/dist/core/runtime/tmux-driver.js +7 -637
  611. package/dist/core/runtime/tool-group-summary.js +6 -85
  612. package/dist/core/runtime/turn-visibility.js +1 -31
  613. package/dist/core/runtime/view-socket.js +1 -83
  614. package/dist/core/runtime/warm-pool.js +1 -395
  615. package/dist/core/scope.js +1 -254
  616. package/dist/core/scoped-state/db.js +1 -135
  617. package/dist/core/scoped-state/migrate.js +3 -181
  618. package/dist/core/scoped-state/paths.js +1 -27
  619. package/dist/core/scoped-state/profiles.js +1 -62
  620. package/dist/core/scoped-state/providers.js +1 -8
  621. package/dist/core/scoped-state/schema.js +3 -16
  622. package/dist/core/scoped-state/settings.js +1 -82
  623. package/dist/core/secrets.js +2 -55
  624. package/dist/core/self-update.js +1 -71
  625. package/dist/core/session-model/session-state.js +1 -180
  626. package/dist/core/shell-segments.js +4 -169
  627. package/dist/core/spawn.js +1 -26
  628. package/dist/core/stdout-errors.js +1 -14
  629. package/dist/core/subscription-state.js +3 -193
  630. package/dist/core/substrate/frontmatter-validation.js +1 -105
  631. package/dist/core/substrate/gate-explain.js +1 -424
  632. package/dist/core/substrate/gate.js +1 -26
  633. package/dist/core/substrate/index.js +1 -30
  634. package/dist/core/substrate/injected-store.js +1 -249
  635. package/dist/core/substrate/listings.js +1 -115
  636. package/dist/core/substrate/on-read-node.js +1 -36
  637. package/dist/core/substrate/on-read.js +9 -315
  638. package/dist/core/substrate/plan.js +1 -266
  639. package/dist/core/substrate/render-node.js +1 -30
  640. package/dist/core/substrate/render.js +65 -689
  641. package/dist/core/substrate/schema.js +1 -186
  642. package/dist/core/substrate/session-cache.js +1 -83
  643. package/dist/core/substrate/subject-fields.js +1 -35
  644. package/dist/core/substrate/subject.js +1 -47
  645. package/dist/core/substrate/surface-match.js +1 -242
  646. package/dist/core/termrender/code-doc.js +5 -92
  647. package/dist/core/termrender/display.js +2 -56
  648. package/dist/core/termrender/termrender.js +14 -719
  649. package/dist/core/termrender/version.js +1 -1
  650. package/dist/core/timing.js +2 -94
  651. package/dist/core/tui/draw.js +2 -378
  652. package/dist/core/tui/fuzzy.js +1 -38
  653. package/dist/core/tui/markdown.js +3 -407
  654. package/dist/core/tui/page-host.js +1 -74
  655. package/dist/core/tui/panel.js +1 -137
  656. package/dist/core/tui/terminal.js +2 -100
  657. package/dist/core/user-settings.js +1 -454
  658. package/dist/core/wake.js +1 -296
  659. package/dist/core/worktree-close.js +6 -228
  660. package/dist/core/worktree-containment.js +3 -48
  661. package/dist/core/worktree-landing.js +4 -56
  662. package/dist/core/worktree-mutation-async.js +10 -280
  663. package/dist/core/worktree-quarantine.js +1 -54
  664. package/dist/core/worktree-sweep.js +6 -453
  665. package/dist/core/worktree.js +18 -899
  666. package/dist/daemon/api/bridge.js +8 -418
  667. package/dist/daemon/api/handlers/attach.js +1 -65
  668. package/dist/daemon/api/handlers/bash-jobs.js +2 -91
  669. package/dist/daemon/api/handlers/broker-ops.js +1 -447
  670. package/dist/daemon/api/handlers/broker-recovery.js +1 -251
  671. package/dist/daemon/api/handlers/canvas.js +6 -490
  672. package/dist/daemon/api/handlers/chat-inventory.js +1 -25
  673. package/dist/daemon/api/handlers/crons.js +1 -373
  674. package/dist/daemon/api/handlers/daemon.js +1 -76
  675. package/dist/daemon/api/handlers/feedback-comments.js +3 -199
  676. package/dist/daemon/api/handlers/files.js +1 -63
  677. package/dist/daemon/api/handlers/focus.js +1 -92
  678. package/dist/daemon/api/handlers/health.js +1 -76
  679. package/dist/daemon/api/handlers/human-requests.js +1 -379
  680. package/dist/daemon/api/handlers/human.js +1 -3
  681. package/dist/daemon/api/handlers/inbox-page.js +1 -89
  682. package/dist/daemon/api/handlers/inbox.js +1 -301
  683. package/dist/daemon/api/handlers/memory.js +1 -50
  684. package/dist/daemon/api/handlers/messages.js +2 -506
  685. package/dist/daemon/api/handlers/model-config.js +1 -44
  686. package/dist/daemon/api/handlers/modelauth.js +1 -165
  687. package/dist/daemon/api/handlers/node-outcomes.js +1 -181
  688. package/dist/daemon/api/handlers/nodes.js +1 -939
  689. package/dist/daemon/api/handlers/profiles.js +1 -140
  690. package/dist/daemon/api/handlers/prospective-chat-inventory.js +1 -59
  691. package/dist/daemon/api/handlers/reports.js +16 -332
  692. package/dist/daemon/api/handlers/review-comments.js +1 -465
  693. package/dist/daemon/api/handlers/reviews.js +1 -200
  694. package/dist/daemon/api/handlers/subscriptions.js +1 -53
  695. package/dist/daemon/api/handlers/validate.js +1 -58
  696. package/dist/daemon/api/handlers/worktree.js +1 -39
  697. package/dist/daemon/api/map.js +2 -735
  698. package/dist/daemon/api/router.js +1 -190
  699. package/dist/daemon/api/server.js +11 -408
  700. package/dist/daemon/boot-migrations.js +1 -31
  701. package/dist/daemon/companion-retire.js +1 -34
  702. package/dist/daemon/control.js +1 -22
  703. package/dist/daemon/cron/armed-context.js +1 -100
  704. package/dist/daemon/cron/capture.js +2 -45
  705. package/dist/daemon/cron/disposition.js +1 -55
  706. package/dist/daemon/cron/escalation.js +3 -124
  707. package/dist/daemon/cron/held.js +1 -20
  708. package/dist/daemon/cron/lease-recovery.js +1 -119
  709. package/dist/daemon/cron/live-runs.js +1 -23
  710. package/dist/daemon/cron/passes.js +1 -58
  711. package/dist/daemon/cron/settle.js +1 -61
  712. package/dist/daemon/cron/sinks.js +2 -59
  713. package/dist/daemon/cron-run.js +1 -405
  714. package/dist/daemon/crtrd-cli.js +1 -23
  715. package/dist/daemon/crtrd.js +8 -854
  716. package/dist/daemon/delivery/run-delivery.js +1 -164
  717. package/dist/daemon/fleet.js +17 -475
  718. package/dist/daemon/human/finish.js +10 -179
  719. package/dist/daemon/human/settle.js +1 -89
  720. package/dist/daemon/human/sweep.js +1 -66
  721. package/dist/daemon/manage.js +2 -595
  722. package/dist/daemon/messaging/node-message.js +1 -99
  723. package/dist/daemon/park-activity.js +1 -30
  724. package/dist/daemon/park-pending.js +1 -52
  725. package/dist/daemon/pidfile.js +1 -37
  726. package/dist/daemon/profile-delete.js +1 -306
  727. package/dist/daemon/reconcilers/bash-deadline.js +1 -80
  728. package/dist/daemon/reconcilers/broker-supervision.js +4 -761
  729. package/dist/daemon/reconcilers/controller-death.js +1 -14
  730. package/dist/daemon/reconcilers/cron-lane.js +1 -29
  731. package/dist/daemon/reconcilers/delivery-lane.js +1 -130
  732. package/dist/daemon/reconcilers/live-obligation.js +1 -87
  733. package/dist/daemon/reconcilers/managed-worktree-sweep.js +1 -202
  734. package/dist/daemon/reconcilers/node-deadline.js +1 -82
  735. package/dist/daemon/reconcilers/node-lifecycle/freeze-lane.js +1 -172
  736. package/dist/daemon/reconcilers/node-lifecycle/respawn-policy.js +1 -59
  737. package/dist/daemon/reconcilers/node-lifecycle/terminating.js +1 -12
  738. package/dist/daemon/reconcilers/node-lifecycle/tick.js +1 -146
  739. package/dist/daemon/reconcilers/node-lifecycle/wants-execution.js +1 -11
  740. package/dist/daemon/reconcilers/pending-review-submit.js +1 -36
  741. package/dist/daemon/reconcilers/storage-maintenance.js +1 -207
  742. package/dist/daemon/review/comment-notify.js +2 -109
  743. package/dist/daemon/review/companion.js +1 -29
  744. package/dist/daemon/review/deliver.js +3 -8
  745. package/dist/daemon/review/finish.js +1 -122
  746. package/dist/daemon/review/sweep.js +1 -18
  747. package/dist/daemon/startup-policy.js +1 -1
  748. package/dist/daemon/supervise-cadence.js +1 -6
  749. package/dist/hook-authoring.js +5 -447
  750. package/dist/hook-process.js +1 -34
  751. package/dist/index.js +1 -52
  752. package/dist/migrations/001-surfaces-frontmatter.js +1 -161
  753. package/dist/migrations/002-profile-project-memory.js +1 -72
  754. package/dist/migrations/003-repository-root-memory-identity/front-door.js +11 -231
  755. package/dist/migrations/003-repository-root-memory-identity/index.js +5 -513
  756. package/dist/migrations/003-repository-root-memory-identity/references.js +5 -469
  757. package/dist/migrations/003-repository-root-memory-identity/repository-facts.js +3 -349
  758. package/dist/migrations/activation.js +2 -89
  759. package/dist/migrations/convergent.js +2 -82
  760. package/dist/migrations/corpus.js +3 -483
  761. package/dist/migrations/frontmatter-splice.js +8 -176
  762. package/dist/migrations/profile-manifests.js +2 -70
  763. package/dist/migrations/registry.js +1 -42
  764. package/dist/migrations/runner.js +1 -85
  765. package/dist/migrations/types.js +0 -24
  766. package/dist/pi-extensions/broker-local.js +2 -106
  767. package/dist/pi-extensions/canvas-bash-valve.js +7 -461
  768. package/dist/pi-extensions/canvas-context-intro.js +2 -113
  769. package/dist/pi-extensions/canvas-doc-substrate.js +9 -178
  770. package/dist/pi-extensions/canvas-goal-capture.js +1 -83
  771. package/dist/pi-extensions/canvas-inbox-watcher.js +1 -1010
  772. package/dist/pi-extensions/canvas-passive-context.js +14 -203
  773. package/dist/pi-extensions/canvas-preview-result.js +2 -72
  774. package/dist/pi-extensions/canvas-prompt-scrub.js +2 -54
  775. package/dist/pi-extensions/canvas-recap.js +11 -405
  776. package/dist/pi-extensions/canvas-review-boundary.js +3 -63
  777. package/dist/pi-extensions/canvas-stamp.js +2 -77
  778. package/dist/pi-extensions/canvas-stophook.js +1 -643
  779. package/dist/pi-extensions/canvas-structured-output.js +13 -35
  780. package/dist/pi-extensions/canvas-tool-guide.js +9 -78
  781. package/dist/pi-extensions/envelope-merge.js +8 -29
  782. package/dist/prompts/review.js +20 -42
  783. package/dist/shared/birth-announcement.js +1 -25
  784. package/dist/shared/crtr-version.js +1 -18
  785. package/dist/shared/env.js +1 -214
  786. package/dist/shared/generated-context.js +11 -226
  787. package/dist/shared/predicates.js +1 -4
  788. package/dist/shared/shell-quote.js +1 -5
  789. package/dist/shared/tool-groups.js +1 -64
  790. package/dist/shared/working-activity.js +1 -27
  791. package/dist/suppress-experimental-warnings.js +1 -15
  792. package/dist/types.js +1 -185
  793. package/docs/public-api.md +10 -9
  794. package/package.json +5 -4
  795. package/runtime.lock.json +5 -5
  796. package/dist/api/__tests__/integration/client.test.d.ts +0 -1
  797. package/dist/api/__tests__/integration/client.test.js +0 -163
  798. package/dist/builtin-pi-packages/pi-crtr-extensions/__tests__/insights-active-init.test.ts +0 -98
  799. package/dist/builtin-pi-packages/pi-crtr-extensions/extensions/__tests__/crtr-commands.test.ts +0 -93
  800. package/dist/builtin-pi-packages/pi-crtr-extensions/extensions/__tests__/integration/provider-rotation.test.ts +0 -2530
  801. package/dist/clients/__tests__/helpers/human-daemon.d.ts +0 -11
  802. package/dist/clients/__tests__/helpers/human-daemon.js +0 -60
  803. package/dist/clients/attach/__tests__/attach-remote-readonly.test.d.ts +0 -1
  804. package/dist/clients/attach/__tests__/attach-remote-readonly.test.js +0 -97
  805. package/dist/clients/attach/__tests__/bash-call-width.test.d.ts +0 -1
  806. package/dist/clients/attach/__tests__/bash-call-width.test.js +0 -38
  807. package/dist/clients/attach/__tests__/chat-view-snapshot-ordering.test.d.ts +0 -1
  808. package/dist/clients/attach/__tests__/chat-view-snapshot-ordering.test.js +0 -175
  809. package/dist/clients/attach/__tests__/completion-frecency.test.d.ts +0 -1
  810. package/dist/clients/attach/__tests__/completion-frecency.test.js +0 -35
  811. package/dist/clients/attach/__tests__/context-message.test.d.ts +0 -1
  812. package/dist/clients/attach/__tests__/context-message.test.js +0 -130
  813. package/dist/clients/attach/__tests__/crtr-output.test.d.ts +0 -1
  814. package/dist/clients/attach/__tests__/crtr-output.test.js +0 -68
  815. package/dist/clients/attach/__tests__/diagram.test.d.ts +0 -1
  816. package/dist/clients/attach/__tests__/diagram.test.js +0 -42
  817. package/dist/clients/attach/__tests__/edit-diff.test.d.ts +0 -1
  818. package/dist/clients/attach/__tests__/edit-diff.test.js +0 -31
  819. package/dist/clients/attach/__tests__/frame-selection.test.d.ts +0 -1
  820. package/dist/clients/attach/__tests__/frame-selection.test.js +0 -84
  821. package/dist/clients/attach/__tests__/group-activity.test.d.ts +0 -1
  822. package/dist/clients/attach/__tests__/group-activity.test.js +0 -165
  823. package/dist/clients/attach/__tests__/oauth-dialog-lifecycle.test.d.ts +0 -1
  824. package/dist/clients/attach/__tests__/oauth-dialog-lifecycle.test.js +0 -83
  825. package/dist/clients/attach/__tests__/pane-tag-successor.test.d.ts +0 -1
  826. package/dist/clients/attach/__tests__/pane-tag-successor.test.js +0 -56
  827. package/dist/clients/attach/__tests__/profile-files.test.d.ts +0 -1
  828. package/dist/clients/attach/__tests__/profile-files.test.js +0 -21
  829. package/dist/clients/attach/__tests__/prompt-preview.test.d.ts +0 -1
  830. package/dist/clients/attach/__tests__/prompt-preview.test.js +0 -21
  831. package/dist/clients/attach/__tests__/ref-autocomplete.test.d.ts +0 -1
  832. package/dist/clients/attach/__tests__/ref-autocomplete.test.js +0 -64
  833. package/dist/clients/attach/__tests__/titled-editor-paste.test.d.ts +0 -1
  834. package/dist/clients/attach/__tests__/titled-editor-paste.test.js +0 -114
  835. package/dist/clients/attach/__tests__/titled-editor-preview.test.d.ts +0 -1
  836. package/dist/clients/attach/__tests__/titled-editor-preview.test.js +0 -83
  837. package/dist/clients/inbox/__tests__/integration/inbox-controller.test.d.ts +0 -1
  838. package/dist/clients/inbox/__tests__/integration/inbox-controller.test.js +0 -81
  839. package/dist/clients/inbox/__tests__/integration/mount-panel.test.d.ts +0 -1
  840. package/dist/clients/inbox/__tests__/integration/mount-panel.test.js +0 -135
  841. package/dist/clients/inbox/__tests__/integration/stale-row-activation.test.d.ts +0 -1
  842. package/dist/clients/inbox/__tests__/integration/stale-row-activation.test.js +0 -66
  843. package/dist/clients/inbox/review/__tests__/editor-roundtrip.test.d.ts +0 -1
  844. package/dist/clients/inbox/review/__tests__/editor-roundtrip.test.js +0 -35
  845. package/dist/clients/inbox/review/__tests__/review-core.test.d.ts +0 -1
  846. package/dist/clients/inbox/review/__tests__/review-core.test.js +0 -52
  847. package/dist/clients/inbox/review/__tests__/teardown-notice.test.d.ts +0 -1
  848. package/dist/clients/inbox/review/__tests__/teardown-notice.test.js +0 -100
  849. package/dist/commands/__tests__/api-client-cold-start-diagnostic.test.d.ts +0 -1
  850. package/dist/commands/__tests__/api-client-cold-start-diagnostic.test.js +0 -69
  851. package/dist/commands/__tests__/human.test.d.ts +0 -1
  852. package/dist/commands/__tests__/human.test.js +0 -172
  853. package/dist/commands/__tests__/integration/dashboard-snapshot.test.d.ts +0 -1
  854. package/dist/commands/__tests__/integration/dashboard-snapshot.test.js +0 -237
  855. package/dist/commands/__tests__/integration/migrate.test.d.ts +0 -1
  856. package/dist/commands/__tests__/integration/migrate.test.js +0 -1330
  857. package/dist/commands/__tests__/node-message.test.d.ts +0 -1
  858. package/dist/commands/__tests__/node-message.test.js +0 -112
  859. package/dist/commands/__tests__/node-new.test.d.ts +0 -1
  860. package/dist/commands/__tests__/node-new.test.js +0 -58
  861. package/dist/commands/__tests__/revive-now-gate.test.d.ts +0 -1
  862. package/dist/commands/__tests__/revive-now-gate.test.js +0 -62
  863. package/dist/commands/__tests__/seam/daemon-status.test.d.ts +0 -1
  864. package/dist/commands/__tests__/seam/daemon-status.test.js +0 -29
  865. package/dist/commands/__tests__/surface-reload-target.test.d.ts +0 -1
  866. package/dist/commands/__tests__/surface-reload-target.test.js +0 -21
  867. package/dist/commands/memory/__tests__/command-selector-and-mutation-guards.test.d.ts +0 -1
  868. package/dist/commands/memory/__tests__/command-selector-and-mutation-guards.test.js +0 -379
  869. package/dist/commands/memory/__tests__/memory-list-and-lint-ignore.test.d.ts +0 -1
  870. package/dist/commands/memory/__tests__/memory-list-and-lint-ignore.test.js +0 -124
  871. package/dist/commands/memory/__tests__/repository-root-lint.test.d.ts +0 -1
  872. package/dist/commands/memory/__tests__/repository-root-lint.test.js +0 -148
  873. package/dist/commands/sys/__tests__/config-model-ladders.test.d.ts +0 -1
  874. package/dist/commands/sys/__tests__/config-model-ladders.test.js +0 -114
  875. package/dist/commands/sys/__tests__/setup-core.test.d.ts +0 -1
  876. package/dist/commands/sys/__tests__/setup-core.test.js +0 -45
  877. package/dist/commands/sys/__tests__/sync-project-guidance.test.d.ts +0 -1
  878. package/dist/commands/sys/__tests__/sync-project-guidance.test.js +0 -244
  879. package/dist/core/__tests__/bash-guard.test.d.ts +0 -1
  880. package/dist/core/__tests__/bash-guard.test.js +0 -190
  881. package/dist/core/__tests__/boot-fault-attempt.test.d.ts +0 -1
  882. package/dist/core/__tests__/boot-fault-attempt.test.js +0 -105
  883. package/dist/core/__tests__/boot.test.d.ts +0 -1
  884. package/dist/core/__tests__/boot.test.js +0 -274
  885. package/dist/core/__tests__/branded-host-concurrency.test.d.ts +0 -1
  886. package/dist/core/__tests__/branded-host-concurrency.test.js +0 -72
  887. package/dist/core/__tests__/broker-extension-canvas-db-boundary.test.d.ts +0 -1
  888. package/dist/core/__tests__/broker-extension-canvas-db-boundary.test.js +0 -75
  889. package/dist/core/__tests__/broker-launch-candidates.test.d.ts +0 -1
  890. package/dist/core/__tests__/broker-launch-candidates.test.js +0 -311
  891. package/dist/core/__tests__/broker-preflight.test.d.ts +0 -1
  892. package/dist/core/__tests__/broker-preflight.test.js +0 -95
  893. package/dist/core/__tests__/broker-stream-watchdog-floor.test.d.ts +0 -1
  894. package/dist/core/__tests__/broker-stream-watchdog-floor.test.js +0 -82
  895. package/dist/core/__tests__/broker-turn-admission.test.d.ts +0 -1
  896. package/dist/core/__tests__/broker-turn-admission.test.js +0 -44
  897. package/dist/core/__tests__/canvas-db-boundary.test.d.ts +0 -1
  898. package/dist/core/__tests__/canvas-db-boundary.test.js +0 -46
  899. package/dist/core/__tests__/canvas-inbox-watcher-hold.test.d.ts +0 -1
  900. package/dist/core/__tests__/canvas-inbox-watcher-hold.test.js +0 -710
  901. package/dist/core/__tests__/canvas-inbox-watcher-naming.test.d.ts +0 -1
  902. package/dist/core/__tests__/canvas-inbox-watcher-naming.test.js +0 -310
  903. package/dist/core/__tests__/canvas-inbox-watcher.test.d.ts +0 -1
  904. package/dist/core/__tests__/canvas-inbox-watcher.test.js +0 -397
  905. package/dist/core/__tests__/canvas.test.d.ts +0 -1
  906. package/dist/core/__tests__/canvas.test.js +0 -138
  907. package/dist/core/__tests__/child-death-wake.test.d.ts +0 -1
  908. package/dist/core/__tests__/child-death-wake.test.js +0 -153
  909. package/dist/core/__tests__/cli-help-contract.test.d.ts +0 -1
  910. package/dist/core/__tests__/cli-help-contract.test.js +0 -152
  911. package/dist/core/__tests__/close.test.d.ts +0 -1
  912. package/dist/core/__tests__/close.test.js +0 -284
  913. package/dist/core/__tests__/collectible.test.d.ts +0 -1
  914. package/dist/core/__tests__/collectible.test.js +0 -89
  915. package/dist/core/__tests__/config-change-delta.test.d.ts +0 -1
  916. package/dist/core/__tests__/config-change-delta.test.js +0 -108
  917. package/dist/core/__tests__/context-intro.test.d.ts +0 -1
  918. package/dist/core/__tests__/context-intro.test.js +0 -123
  919. package/dist/core/__tests__/cron-armed-context-failure.test.d.ts +0 -1
  920. package/dist/core/__tests__/cron-armed-context-failure.test.js +0 -150
  921. package/dist/core/__tests__/cron-held-settlement.test.d.ts +0 -1
  922. package/dist/core/__tests__/cron-held-settlement.test.js +0 -240
  923. package/dist/core/__tests__/cron-node-sink-parked-root.test.d.ts +0 -1
  924. package/dist/core/__tests__/cron-node-sink-parked-root.test.js +0 -166
  925. package/dist/core/__tests__/cron-self-cancel-delivery.test.d.ts +0 -1
  926. package/dist/core/__tests__/cron-self-cancel-delivery.test.js +0 -84
  927. package/dist/core/__tests__/cron-timeout-descendants.test.d.ts +0 -1
  928. package/dist/core/__tests__/cron-timeout-descendants.test.js +0 -114
  929. package/dist/core/__tests__/daemon-boot.test.d.ts +0 -1
  930. package/dist/core/__tests__/daemon-boot.test.js +0 -422
  931. package/dist/core/__tests__/daemon-wedge.test.d.ts +0 -1
  932. package/dist/core/__tests__/daemon-wedge.test.js +0 -106
  933. package/dist/core/__tests__/dead-node-policy-table.test.d.ts +0 -1
  934. package/dist/core/__tests__/dead-node-policy-table.test.js +0 -77
  935. package/dist/core/__tests__/events-contract.test.d.ts +0 -1
  936. package/dist/core/__tests__/events-contract.test.js +0 -76
  937. package/dist/core/__tests__/extension-abort.test.d.ts +0 -1
  938. package/dist/core/__tests__/extension-abort.test.js +0 -21
  939. package/dist/core/__tests__/fault-classifier.test.d.ts +0 -1
  940. package/dist/core/__tests__/fault-classifier.test.js +0 -138
  941. package/dist/core/__tests__/fixtures/api-server-host.d.ts +0 -1
  942. package/dist/core/__tests__/fixtures/api-server-host.js +0 -47
  943. package/dist/core/__tests__/fixtures/c3-custom-provider-ext.d.ts +0 -2
  944. package/dist/core/__tests__/fixtures/c3-custom-provider-ext.js +0 -34
  945. package/dist/core/__tests__/fixtures/c5-command-boundary-ext.d.ts +0 -2
  946. package/dist/core/__tests__/fixtures/c5-command-boundary-ext.js +0 -32
  947. package/dist/core/__tests__/fixtures/fake-engine.d.ts +0 -347
  948. package/dist/core/__tests__/fixtures/fake-engine.js +0 -1509
  949. package/dist/core/__tests__/fixtures/fake-pi-host.d.ts +0 -2
  950. package/dist/core/__tests__/fixtures/fake-pi-host.js +0 -311
  951. package/dist/core/__tests__/fixtures/memory-slash-live-probe.d.ts +0 -1
  952. package/dist/core/__tests__/fixtures/memory-slash-live-probe.js +0 -75
  953. package/dist/core/__tests__/fixtures/metadata-migration-race.d.ts +0 -1
  954. package/dist/core/__tests__/fixtures/metadata-migration-race.js +0 -49
  955. package/dist/core/__tests__/focuses.test.d.ts +0 -1
  956. package/dist/core/__tests__/focuses.test.js +0 -113
  957. package/dist/core/__tests__/fs-utils.test.d.ts +0 -1
  958. package/dist/core/__tests__/fs-utils.test.js +0 -50
  959. package/dist/core/__tests__/helpers/broker-clients.d.ts +0 -43
  960. package/dist/core/__tests__/helpers/broker-clients.js +0 -174
  961. package/dist/core/__tests__/helpers/fleet.d.ts +0 -12
  962. package/dist/core/__tests__/helpers/fleet.js +0 -50
  963. package/dist/core/__tests__/helpers/harness.d.ts +0 -124
  964. package/dist/core/__tests__/helpers/harness.js +0 -806
  965. package/dist/core/__tests__/helpers/viewer-panes.d.ts +0 -12
  966. package/dist/core/__tests__/helpers/viewer-panes.js +0 -133
  967. package/dist/core/__tests__/history-inbox.test.d.ts +0 -1
  968. package/dist/core/__tests__/history-inbox.test.js +0 -121
  969. package/dist/core/__tests__/human-action-delivery.test.d.ts +0 -1
  970. package/dist/core/__tests__/human-action-delivery.test.js +0 -162
  971. package/dist/core/__tests__/human-actions.test.d.ts +0 -1
  972. package/dist/core/__tests__/human-actions.test.js +0 -120
  973. package/dist/core/__tests__/inline-memory-refs.test.d.ts +0 -1
  974. package/dist/core/__tests__/inline-memory-refs.test.js +0 -225
  975. package/dist/core/__tests__/integration/broker-fork-seam.test.d.ts +0 -1
  976. package/dist/core/__tests__/integration/broker-fork-seam.test.js +0 -193
  977. package/dist/core/__tests__/integration/broker-sdk-wiring.test.d.ts +0 -1
  978. package/dist/core/__tests__/integration/broker-sdk-wiring.test.js +0 -750
  979. package/dist/core/__tests__/integration/broker-snapshot-history.test.d.ts +0 -1
  980. package/dist/core/__tests__/integration/broker-snapshot-history.test.js +0 -288
  981. package/dist/core/__tests__/integration/broker-wedge-supervision.test.d.ts +0 -1
  982. package/dist/core/__tests__/integration/broker-wedge-supervision.test.js +0 -103
  983. package/dist/core/__tests__/integration/command-plugins.test.d.ts +0 -1
  984. package/dist/core/__tests__/integration/command-plugins.test.js +0 -1200
  985. package/dist/core/__tests__/integration/deferred-no-wake.test.d.ts +0 -1
  986. package/dist/core/__tests__/integration/deferred-no-wake.test.js +0 -610
  987. package/dist/core/__tests__/integration/flagship-lifecycle.test.d.ts +0 -1
  988. package/dist/core/__tests__/integration/flagship-lifecycle.test.js +0 -264
  989. package/dist/core/__tests__/integration/fresh-home-commands.test.d.ts +0 -1
  990. package/dist/core/__tests__/integration/fresh-home-commands.test.js +0 -49
  991. package/dist/core/__tests__/integration/git-optional-locks.test.d.ts +0 -1
  992. package/dist/core/__tests__/integration/git-optional-locks.test.js +0 -81
  993. package/dist/core/__tests__/integration/host-teardown-process-group.test.d.ts +0 -1
  994. package/dist/core/__tests__/integration/host-teardown-process-group.test.js +0 -480
  995. package/dist/core/__tests__/integration/lifecycle-hooks.test.d.ts +0 -1
  996. package/dist/core/__tests__/integration/lifecycle-hooks.test.js +0 -498
  997. package/dist/core/__tests__/integration/live-mutation-verbs.test.d.ts +0 -1
  998. package/dist/core/__tests__/integration/live-mutation-verbs.test.js +0 -180
  999. package/dist/core/__tests__/integration/live-mutation.test.d.ts +0 -1
  1000. package/dist/core/__tests__/integration/live-mutation.test.js +0 -173
  1001. package/dist/core/__tests__/integration/plugin-revalidate.test.d.ts +0 -1
  1002. package/dist/core/__tests__/integration/plugin-revalidate.test.js +0 -359
  1003. package/dist/core/__tests__/integration/profile-pause.test.d.ts +0 -1
  1004. package/dist/core/__tests__/integration/profile-pause.test.js +0 -115
  1005. package/dist/core/__tests__/integration/refresh-stall-recycle.test.d.ts +0 -1
  1006. package/dist/core/__tests__/integration/refresh-stall-recycle.test.js +0 -151
  1007. package/dist/core/__tests__/integration/revive.test.d.ts +0 -1
  1008. package/dist/core/__tests__/integration/revive.test.js +0 -615
  1009. package/dist/core/__tests__/integration/spawn-root.test.d.ts +0 -1
  1010. package/dist/core/__tests__/integration/spawn-root.test.js +0 -536
  1011. package/dist/core/__tests__/integration/subscription-delivery.test.d.ts +0 -1
  1012. package/dist/core/__tests__/integration/subscription-delivery.test.js +0 -132
  1013. package/dist/core/__tests__/integration/tmux-surface.test.d.ts +0 -1
  1014. package/dist/core/__tests__/integration/tmux-surface.test.js +0 -330
  1015. package/dist/core/__tests__/integration/worktree-land.test.d.ts +0 -1
  1016. package/dist/core/__tests__/integration/worktree-land.test.js +0 -607
  1017. package/dist/core/__tests__/integration/worktree-reap.test.d.ts +0 -1
  1018. package/dist/core/__tests__/integration/worktree-reap.test.js +0 -842
  1019. package/dist/core/__tests__/kickoff.test.d.ts +0 -1
  1020. package/dist/core/__tests__/kickoff.test.js +0 -196
  1021. package/dist/core/__tests__/lifecycle-terminal-reasons.test.d.ts +0 -1
  1022. package/dist/core/__tests__/lifecycle-terminal-reasons.test.js +0 -62
  1023. package/dist/core/__tests__/lifecycle.test.d.ts +0 -1
  1024. package/dist/core/__tests__/lifecycle.test.js +0 -176
  1025. package/dist/core/__tests__/live-lifecycle-prompt.test.d.ts +0 -1
  1026. package/dist/core/__tests__/live-lifecycle-prompt.test.js +0 -63
  1027. package/dist/core/__tests__/memory-resolver-precedence.test.d.ts +0 -1
  1028. package/dist/core/__tests__/memory-resolver-precedence.test.js +0 -228
  1029. package/dist/core/__tests__/migration.test.d.ts +0 -1
  1030. package/dist/core/__tests__/migration.test.js +0 -946
  1031. package/dist/core/__tests__/model-pin-durability.test.d.ts +0 -1
  1032. package/dist/core/__tests__/model-pin-durability.test.js +0 -195
  1033. package/dist/core/__tests__/model-routes-config.test.d.ts +0 -1
  1034. package/dist/core/__tests__/model-routes-config.test.js +0 -150
  1035. package/dist/core/__tests__/nested-store-discovery.test.d.ts +0 -1
  1036. package/dist/core/__tests__/nested-store-discovery.test.js +0 -89
  1037. package/dist/core/__tests__/node-outcome.test.d.ts +0 -1
  1038. package/dist/core/__tests__/node-outcome.test.js +0 -246
  1039. package/dist/core/__tests__/on-read-crouter-home-fence.test.d.ts +0 -1
  1040. package/dist/core/__tests__/on-read-crouter-home-fence.test.js +0 -66
  1041. package/dist/core/__tests__/on-read-dedup-resume.test.d.ts +0 -1
  1042. package/dist/core/__tests__/on-read-dedup-resume.test.js +0 -132
  1043. package/dist/core/__tests__/on-read-nested-store.test.d.ts +0 -1
  1044. package/dist/core/__tests__/on-read-nested-store.test.js +0 -135
  1045. package/dist/core/__tests__/parse-argv-stdin-secret.test.d.ts +0 -1
  1046. package/dist/core/__tests__/parse-argv-stdin-secret.test.js +0 -68
  1047. package/dist/core/__tests__/passive-subscription.test.d.ts +0 -1
  1048. package/dist/core/__tests__/passive-subscription.test.js +0 -120
  1049. package/dist/core/__tests__/pid-identity-match.test.d.ts +0 -1
  1050. package/dist/core/__tests__/pid-identity-match.test.js +0 -145
  1051. package/dist/core/__tests__/pid-zombie.test.d.ts +0 -1
  1052. package/dist/core/__tests__/pid-zombie.test.js +0 -42
  1053. package/dist/core/__tests__/plugin-kinds.test.d.ts +0 -1
  1054. package/dist/core/__tests__/plugin-kinds.test.js +0 -182
  1055. package/dist/core/__tests__/plugin-link-symlinked-scope-root.test.d.ts +0 -1
  1056. package/dist/core/__tests__/plugin-link-symlinked-scope-root.test.js +0 -43
  1057. package/dist/core/__tests__/plugin-page-components.test.d.ts +0 -1
  1058. package/dist/core/__tests__/plugin-page-components.test.js +0 -159
  1059. package/dist/core/__tests__/preview-mirror-cap.test.d.ts +0 -1
  1060. package/dist/core/__tests__/preview-mirror-cap.test.js +0 -53
  1061. package/dist/core/__tests__/preview-registry-sync.test.d.ts +0 -1
  1062. package/dist/core/__tests__/preview-registry-sync.test.js +0 -107
  1063. package/dist/core/__tests__/profile-project-memory-delivery.test.d.ts +0 -1
  1064. package/dist/core/__tests__/profile-project-memory-delivery.test.js +0 -644
  1065. package/dist/core/__tests__/prospective-inventory-capability-parity.test.d.ts +0 -1
  1066. package/dist/core/__tests__/prospective-inventory-capability-parity.test.js +0 -91
  1067. package/dist/core/__tests__/prune.test.d.ts +0 -1
  1068. package/dist/core/__tests__/prune.test.js +0 -243
  1069. package/dist/core/__tests__/push-final-guard.test.d.ts +0 -1
  1070. package/dist/core/__tests__/push-final-guard.test.js +0 -191
  1071. package/dist/core/__tests__/relaunch-root.test.d.ts +0 -1
  1072. package/dist/core/__tests__/relaunch-root.test.js +0 -249
  1073. package/dist/core/__tests__/remote-canvas-target.test.d.ts +0 -1
  1074. package/dist/core/__tests__/remote-canvas-target.test.js +0 -93
  1075. package/dist/core/__tests__/repository-association.test.d.ts +0 -1
  1076. package/dist/core/__tests__/repository-association.test.js +0 -153
  1077. package/dist/core/__tests__/repository-root-identity.test.d.ts +0 -1
  1078. package/dist/core/__tests__/repository-root-identity.test.js +0 -223
  1079. package/dist/core/__tests__/respawn-throttle.test.d.ts +0 -1
  1080. package/dist/core/__tests__/respawn-throttle.test.js +0 -20
  1081. package/dist/core/__tests__/review-model-floor.test.d.ts +0 -1
  1082. package/dist/core/__tests__/review-model-floor.test.js +0 -83
  1083. package/dist/core/__tests__/revive-all.test.d.ts +0 -1
  1084. package/dist/core/__tests__/revive-all.test.js +0 -157
  1085. package/dist/core/__tests__/revive-capacity.test.d.ts +0 -1
  1086. package/dist/core/__tests__/revive-capacity.test.js +0 -184
  1087. package/dist/core/__tests__/revive-parked-fresh.test.d.ts +0 -1
  1088. package/dist/core/__tests__/revive-parked-fresh.test.js +0 -176
  1089. package/dist/core/__tests__/scope-crouter-home-fence.test.d.ts +0 -1
  1090. package/dist/core/__tests__/scope-crouter-home-fence.test.js +0 -55
  1091. package/dist/core/__tests__/seam/broker-attach-multiclient.test.d.ts +0 -1
  1092. package/dist/core/__tests__/seam/broker-attach-multiclient.test.js +0 -262
  1093. package/dist/core/__tests__/seam/broker-attach-stream.test.d.ts +0 -1
  1094. package/dist/core/__tests__/seam/broker-attach-stream.test.js +0 -176
  1095. package/dist/core/__tests__/seam/broker-cap-freeze.test.d.ts +0 -1
  1096. package/dist/core/__tests__/seam/broker-cap-freeze.test.js +0 -155
  1097. package/dist/core/__tests__/seam/broker-crash-teardown.test.d.ts +0 -1
  1098. package/dist/core/__tests__/seam/broker-crash-teardown.test.js +0 -131
  1099. package/dist/core/__tests__/seam/broker-pane-resolution.test.d.ts +0 -1
  1100. package/dist/core/__tests__/seam/broker-pane-resolution.test.js +0 -204
  1101. package/dist/core/__tests__/seam/broker-provider-retry.test.d.ts +0 -1
  1102. package/dist/core/__tests__/seam/broker-provider-retry.test.js +0 -686
  1103. package/dist/core/__tests__/seam/broker-startup-diagnostics.test.d.ts +0 -1
  1104. package/dist/core/__tests__/seam/broker-startup-diagnostics.test.js +0 -82
  1105. package/dist/core/__tests__/seam/broker-whip-interrupt.test.d.ts +0 -1
  1106. package/dist/core/__tests__/seam/broker-whip-interrupt.test.js +0 -50
  1107. package/dist/core/__tests__/seam/deadline-wake-delivery.test.d.ts +0 -1
  1108. package/dist/core/__tests__/seam/deadline-wake-delivery.test.js +0 -138
  1109. package/dist/core/__tests__/seam/dormancy-release.test.d.ts +0 -1
  1110. package/dist/core/__tests__/seam/dormancy-release.test.js +0 -516
  1111. package/dist/core/__tests__/seam/held-deferred-human-prompt.test.d.ts +0 -1
  1112. package/dist/core/__tests__/seam/held-deferred-human-prompt.test.js +0 -65
  1113. package/dist/core/__tests__/seam/inbox-reference-guidance.test.d.ts +0 -1
  1114. package/dist/core/__tests__/seam/inbox-reference-guidance.test.js +0 -84
  1115. package/dist/core/__tests__/seam/memory-slash-node-relative-inventory.test.d.ts +0 -1
  1116. package/dist/core/__tests__/seam/memory-slash-node-relative-inventory.test.js +0 -160
  1117. package/dist/core/__tests__/seam/node-outcome-delivery.test.d.ts +0 -1
  1118. package/dist/core/__tests__/seam/node-outcome-delivery.test.js +0 -177
  1119. package/dist/core/__tests__/seam/prospective-inventory-stdout.test.d.ts +0 -1
  1120. package/dist/core/__tests__/seam/prospective-inventory-stdout.test.js +0 -31
  1121. package/dist/core/__tests__/seam/reopen-invalidated-worktree.test.d.ts +0 -1
  1122. package/dist/core/__tests__/seam/reopen-invalidated-worktree.test.js +0 -60
  1123. package/dist/core/__tests__/seam/self-close-teardown.test.d.ts +0 -1
  1124. package/dist/core/__tests__/seam/self-close-teardown.test.js +0 -49
  1125. package/dist/core/__tests__/seam/yield-refresh-transaction.test.d.ts +0 -1
  1126. package/dist/core/__tests__/seam/yield-refresh-transaction.test.js +0 -100
  1127. package/dist/core/__tests__/secrets.test.d.ts +0 -1
  1128. package/dist/core/__tests__/secrets.test.js +0 -49
  1129. package/dist/core/__tests__/self-update.test.d.ts +0 -1
  1130. package/dist/core/__tests__/self-update.test.js +0 -46
  1131. package/dist/core/__tests__/session-branch.test.d.ts +0 -1
  1132. package/dist/core/__tests__/session-branch.test.js +0 -61
  1133. package/dist/core/__tests__/session-cycles.test.d.ts +0 -1
  1134. package/dist/core/__tests__/session-cycles.test.js +0 -133
  1135. package/dist/core/__tests__/session-model.test.d.ts +0 -1
  1136. package/dist/core/__tests__/session-model.test.js +0 -111
  1137. package/dist/core/__tests__/spawn-worktree-id-conflict.test.d.ts +0 -1
  1138. package/dist/core/__tests__/spawn-worktree-id-conflict.test.js +0 -71
  1139. package/dist/core/__tests__/stdin-body-no-discard.test.d.ts +0 -1
  1140. package/dist/core/__tests__/stdin-body-no-discard.test.js +0 -33
  1141. package/dist/core/__tests__/stdout-errors.test.d.ts +0 -1
  1142. package/dist/core/__tests__/stdout-errors.test.js +0 -16
  1143. package/dist/core/__tests__/stop-guard.test.d.ts +0 -1
  1144. package/dist/core/__tests__/stop-guard.test.js +0 -237
  1145. package/dist/core/__tests__/stream-watchdog.test.d.ts +0 -1
  1146. package/dist/core/__tests__/stream-watchdog.test.js +0 -154
  1147. package/dist/core/__tests__/subscription-pool-credential-guard.test.d.ts +0 -1
  1148. package/dist/core/__tests__/subscription-pool-credential-guard.test.js +0 -95
  1149. package/dist/core/__tests__/tmux-driver-boundary.test.d.ts +0 -1
  1150. package/dist/core/__tests__/tmux-driver-boundary.test.js +0 -50
  1151. package/dist/core/__tests__/warm-claim-preference-snapshot.test.d.ts +0 -1
  1152. package/dist/core/__tests__/warm-claim-preference-snapshot.test.js +0 -54
  1153. package/dist/core/__tests__/worktree-landing.test.d.ts +0 -1
  1154. package/dist/core/__tests__/worktree-landing.test.js +0 -11
  1155. package/dist/core/__tests__/yield-ensures-daemon.test.d.ts +0 -1
  1156. package/dist/core/__tests__/yield-ensures-daemon.test.js +0 -55
  1157. package/dist/core/broker-client/__tests__/transport-relay.test.d.ts +0 -1
  1158. package/dist/core/broker-client/__tests__/transport-relay.test.js +0 -214
  1159. package/dist/core/broker-client/__tests__/transport-socket.test.d.ts +0 -1
  1160. package/dist/core/broker-client/__tests__/transport-socket.test.js +0 -73
  1161. package/dist/core/canvas/__tests__/attention.test.d.ts +0 -1
  1162. package/dist/core/canvas/__tests__/attention.test.js +0 -83
  1163. package/dist/core/canvas/__tests__/history-transcript.test.d.ts +0 -1
  1164. package/dist/core/canvas/__tests__/history-transcript.test.js +0 -102
  1165. package/dist/core/canvas/__tests__/remote-canvas-source.test.d.ts +0 -1
  1166. package/dist/core/canvas/__tests__/remote-canvas-source.test.js +0 -328
  1167. package/dist/core/canvas/__tests__/remote-transport.test.d.ts +0 -1
  1168. package/dist/core/canvas/__tests__/remote-transport.test.js +0 -97
  1169. package/dist/core/canvas/__tests__/render-remote.test.d.ts +0 -1
  1170. package/dist/core/canvas/__tests__/render-remote.test.js +0 -243
  1171. package/dist/core/canvas/__tests__/session-window.test.d.ts +0 -1
  1172. package/dist/core/canvas/__tests__/session-window.test.js +0 -70
  1173. package/dist/core/feed/__tests__/inbox-migrate.test.d.ts +0 -1
  1174. package/dist/core/feed/__tests__/inbox-migrate.test.js +0 -49
  1175. package/dist/core/human/__tests__/page-catalog.test.d.ts +0 -1
  1176. package/dist/core/human/__tests__/page-catalog.test.js +0 -20
  1177. package/dist/core/human/__tests__/page-html-markdown.test.d.ts +0 -1
  1178. package/dist/core/human/__tests__/page-html-markdown.test.js +0 -48
  1179. package/dist/core/human/__tests__/page.test.d.ts +0 -1
  1180. package/dist/core/human/__tests__/page.test.js +0 -92
  1181. package/dist/core/keybindings/__tests__/resolve.test.d.ts +0 -1
  1182. package/dist/core/keybindings/__tests__/resolve.test.js +0 -171
  1183. package/dist/core/profiles/__tests__/env-store.test.d.ts +0 -1
  1184. package/dist/core/profiles/__tests__/env-store.test.js +0 -99
  1185. package/dist/core/profiles/__tests__/fuzzy-match.test.d.ts +0 -1
  1186. package/dist/core/profiles/__tests__/fuzzy-match.test.js +0 -51
  1187. package/dist/core/profiles/__tests__/root-profile.test.d.ts +0 -1
  1188. package/dist/core/profiles/__tests__/root-profile.test.js +0 -59
  1189. package/dist/core/review/__tests__/capture-origin.test.d.ts +0 -1
  1190. package/dist/core/review/__tests__/capture-origin.test.js +0 -150
  1191. package/dist/core/review/__tests__/comments.test.d.ts +0 -1
  1192. package/dist/core/review/__tests__/comments.test.js +0 -116
  1193. package/dist/core/review/__tests__/remap.test.d.ts +0 -1
  1194. package/dist/core/review/__tests__/remap.test.js +0 -177
  1195. package/dist/core/review/__tests__/stage-identity.test.d.ts +0 -1
  1196. package/dist/core/review/__tests__/stage-identity.test.js +0 -150
  1197. package/dist/core/runtime/__tests__/engine-route.test.d.ts +0 -1
  1198. package/dist/core/runtime/__tests__/engine-route.test.js +0 -36
  1199. package/dist/core/runtime/__tests__/install-id-cache-scoping.test.d.ts +0 -1
  1200. package/dist/core/runtime/__tests__/install-id-cache-scoping.test.js +0 -45
  1201. package/dist/core/runtime/__tests__/node-env.test.d.ts +0 -1
  1202. package/dist/core/runtime/__tests__/node-env.test.js +0 -73
  1203. package/dist/core/runtime/__tests__/spawn-env.test.d.ts +0 -1
  1204. package/dist/core/runtime/__tests__/spawn-env.test.js +0 -259
  1205. package/dist/core/substrate/__tests__/surface-match-command.test.d.ts +0 -1
  1206. package/dist/core/substrate/__tests__/surface-match-command.test.js +0 -89
  1207. package/dist/core/substrate/__tests__/surface-match-memory-read.test.d.ts +0 -1
  1208. package/dist/core/substrate/__tests__/surface-match-memory-read.test.js +0 -28
  1209. package/dist/core/substrate/__tests__/surface-match-pre-command.test.d.ts +0 -1
  1210. package/dist/core/substrate/__tests__/surface-match-pre-command.test.js +0 -92
  1211. package/dist/daemon/__tests__/autostart-storm.test.d.ts +0 -1
  1212. package/dist/daemon/__tests__/autostart-storm.test.js +0 -128
  1213. package/dist/daemon/__tests__/broker-ownership.test.d.ts +0 -1
  1214. package/dist/daemon/__tests__/broker-ownership.test.js +0 -25
  1215. package/dist/daemon/__tests__/daemon-ownership.test.d.ts +0 -1
  1216. package/dist/daemon/__tests__/daemon-ownership.test.js +0 -27
  1217. package/dist/daemon/__tests__/helpers/source-daemon.d.ts +0 -30
  1218. package/dist/daemon/__tests__/helpers/source-daemon.js +0 -176
  1219. package/dist/daemon/__tests__/integration/api-startup-readiness.test.d.ts +0 -1
  1220. package/dist/daemon/__tests__/integration/api-startup-readiness.test.js +0 -83
  1221. package/dist/daemon/__tests__/integration/migration-startup.test.d.ts +0 -1
  1222. package/dist/daemon/__tests__/integration/migration-startup.test.js +0 -127
  1223. package/dist/daemon/__tests__/node-deadline-lane.test.d.ts +0 -1
  1224. package/dist/daemon/__tests__/node-deadline-lane.test.js +0 -77
  1225. package/dist/daemon/__tests__/node-outcome-birth-invariants.test.d.ts +0 -1
  1226. package/dist/daemon/__tests__/node-outcome-birth-invariants.test.js +0 -146
  1227. package/dist/daemon/__tests__/node-outcome-delivery.test.d.ts +0 -1
  1228. package/dist/daemon/__tests__/node-outcome-delivery.test.js +0 -116
  1229. package/dist/daemon/__tests__/reconciler-signature.test.d.ts +0 -1
  1230. package/dist/daemon/__tests__/reconciler-signature.test.js +0 -37
  1231. package/dist/daemon/__tests__/subtree-filter-freshness.test.d.ts +0 -1
  1232. package/dist/daemon/__tests__/subtree-filter-freshness.test.js +0 -63
  1233. package/dist/daemon/__tests__/thaw-order.test.d.ts +0 -1
  1234. package/dist/daemon/__tests__/thaw-order.test.js +0 -55
  1235. package/dist/daemon/api/__tests__/bridge-heartbeat.test.d.ts +0 -1
  1236. package/dist/daemon/api/__tests__/bridge-heartbeat.test.js +0 -58
  1237. package/dist/daemon/api/__tests__/broker-settle-park.test.d.ts +0 -1
  1238. package/dist/daemon/api/__tests__/broker-settle-park.test.js +0 -175
  1239. package/dist/daemon/api/__tests__/canvas-snapshot-fields.test.d.ts +0 -1
  1240. package/dist/daemon/api/__tests__/canvas-snapshot-fields.test.js +0 -216
  1241. package/dist/daemon/api/__tests__/error-seam.test.d.ts +0 -1
  1242. package/dist/daemon/api/__tests__/error-seam.test.js +0 -83
  1243. package/dist/daemon/api/__tests__/model-config.test.d.ts +0 -1
  1244. package/dist/daemon/api/__tests__/model-config.test.js +0 -73
  1245. package/dist/daemon/api/__tests__/node-create-description.test.d.ts +0 -1
  1246. package/dist/daemon/api/__tests__/node-create-description.test.js +0 -127
  1247. package/dist/daemon/api/__tests__/node-model-validation.test.d.ts +0 -1
  1248. package/dist/daemon/api/__tests__/node-model-validation.test.js +0 -183
  1249. package/dist/daemon/api/__tests__/nodes-activity-query.test.d.ts +0 -1
  1250. package/dist/daemon/api/__tests__/nodes-activity-query.test.js +0 -99
  1251. package/dist/daemon/api/__tests__/profile-launch-gates.test.d.ts +0 -1
  1252. package/dist/daemon/api/__tests__/profile-launch-gates.test.js +0 -172
  1253. package/dist/daemon/api/__tests__/profile-metadata-route.test.d.ts +0 -1
  1254. package/dist/daemon/api/__tests__/profile-metadata-route.test.js +0 -95
  1255. package/dist/daemon/api/__tests__/reopen-delivery.test.d.ts +0 -1
  1256. package/dist/daemon/api/__tests__/reopen-delivery.test.js +0 -260
  1257. package/dist/daemon/api/__tests__/seam/api-server.test.d.ts +0 -1
  1258. package/dist/daemon/api/__tests__/seam/api-server.test.js +0 -442
  1259. package/dist/daemon/api/__tests__/seam/b10-attach-modelauth.test.d.ts +0 -1
  1260. package/dist/daemon/api/__tests__/seam/b10-attach-modelauth.test.js +0 -310
  1261. package/dist/daemon/api/__tests__/seam/leaf-api-parity.test.d.ts +0 -1
  1262. package/dist/daemon/api/__tests__/seam/leaf-api-parity.test.js +0 -351
  1263. package/dist/daemon/api/__tests__/seam/node-outcome-api.test.d.ts +0 -1
  1264. package/dist/daemon/api/__tests__/seam/node-outcome-api.test.js +0 -159
  1265. package/dist/daemon/api/__tests__/seam/profile-delete.test.d.ts +0 -1
  1266. package/dist/daemon/api/__tests__/seam/profile-delete.test.js +0 -372
  1267. package/dist/daemon/api/__tests__/submit-result.test.d.ts +0 -1
  1268. package/dist/daemon/api/__tests__/submit-result.test.js +0 -215
  1269. package/dist/migrations/__tests__/activation-concurrency.test.d.ts +0 -1
  1270. package/dist/migrations/__tests__/activation-concurrency.test.js +0 -146
  1271. package/dist/migrations/__tests__/activation.test.d.ts +0 -1
  1272. package/dist/migrations/__tests__/activation.test.js +0 -152
  1273. package/dist/migrations/__tests__/deletion-and-root-declaration.test.d.ts +0 -1
  1274. package/dist/migrations/__tests__/deletion-and-root-declaration.test.js +0 -149
  1275. package/dist/pi-extensions/__tests__/canvas-bash-valve.test.d.ts +0 -1
  1276. package/dist/pi-extensions/__tests__/canvas-bash-valve.test.js +0 -86
  1277. package/dist/pi-extensions/__tests__/canvas-context-intro.test.d.ts +0 -1
  1278. package/dist/pi-extensions/__tests__/canvas-context-intro.test.js +0 -364
  1279. package/dist/pi-extensions/__tests__/canvas-goal-capture-envelope.test.d.ts +0 -1
  1280. package/dist/pi-extensions/__tests__/canvas-goal-capture-envelope.test.js +0 -106
  1281. package/dist/pi-extensions/__tests__/canvas-recap.test.d.ts +0 -1
  1282. package/dist/pi-extensions/__tests__/canvas-recap.test.js +0 -62
  1283. package/dist/pi-extensions/__tests__/canvas-stophook-agentend.test.d.ts +0 -1
  1284. package/dist/pi-extensions/__tests__/canvas-stophook-agentend.test.js +0 -432
  1285. package/dist/pi-extensions/__tests__/canvas-stophook-context-nudge.test.d.ts +0 -1
  1286. package/dist/pi-extensions/__tests__/canvas-stophook-context-nudge.test.js +0 -152
  1287. package/dist/pi-extensions/__tests__/canvas-structured-output.test.d.ts +0 -1
  1288. package/dist/pi-extensions/__tests__/canvas-structured-output.test.js +0 -88
  1289. package/dist/pi-extensions/__tests__/canvas-tool-guide.test.d.ts +0 -1
  1290. package/dist/pi-extensions/__tests__/canvas-tool-guide.test.js +0 -96
  1291. package/dist/pi-extensions/__tests__/integration/canvas-bash-valve.test.d.ts +0 -1
  1292. package/dist/pi-extensions/__tests__/integration/canvas-bash-valve.test.js +0 -133
  1293. package/dist/pi-extensions/__tests__/pre-command-gate.test.d.ts +0 -1
  1294. package/dist/pi-extensions/__tests__/pre-command-gate.test.js +0 -232
  1295. package/dist/shared/__tests__/env-boundary.test.d.ts +0 -1
  1296. package/dist/shared/__tests__/env-boundary.test.js +0 -95
  1297. package/dist/shared/__tests__/generated-context-grammar.test.d.ts +0 -1
  1298. package/dist/shared/__tests__/generated-context-grammar.test.js +0 -80
  1299. package/docs/compat/hearth-crtr-v1.md +0 -179
  1300. package/docs/compat/hearth-crtr-v2.md +0 -177
  1301. package/docs/compat/hearth-crtr-v3.md +0 -176
  1302. package/docs/compat/hearth-crtr-v4.md +0 -182
  1303. package/docs/compat/hearth-crtr-v5.md +0 -169
@@ -1,52 +1,4 @@
1
- // canvas.db's versioned schema chain — the FIRST of this repo's three
2
- // migration homes. This module owns the v1..vN sequence gated by
3
- // `PRAGMA user_version`: schema DDL, one-time data backfills, and the
4
- // journaled on-disk-lane splice (`../../migrations/registry.ts`'s
5
- // `journaled` entries, appended at the tail of `MIGRATIONS`). A step here
6
- // runs through the daemon's explicit `migrate()` startup call, exactly once per database,
7
- // transactionally.
8
- //
9
- // The other two homes:
10
- // - `../../migrations/registry.ts` — the `STATE_MIGRATIONS` registry for
11
- // on-disk memory documents, profile manifests, and the corpus lane,
12
- // driven by `crtr sys migrate`. Its registrants may import ONLY
13
- // fs/frontmatter utilities — never canvas-db or canvas accessors — so
14
- // the file stays legal in every CLI leaf's import graph. That is why
15
- // this chain (which reads node meta, queries other tables mid-step, and
16
- // builds shell commands from canvas data) is NOT a registrant there.
17
- // - `../../daemon/boot-migrations.ts` — filesystem repairs that run
18
- // unconditionally at every daemon boot, outside any version gate
19
- // (idempotent by their own convergence, not `user_version`).
20
- //
21
- // `db.ts` itself keeps only connection management (`openDb`/`withCanvasWrite`
22
- // /`closeDb`) and re-exports `migrate`/`MIGRATIONS` from here so external
23
- // imports are unaffected by this split.
24
- import { importNodeSqlAuthority } from './node-sql-migration.js';
25
- import { migrateRecoveryWitnesses } from './recovery.js';
26
- import { migrateMessagingState } from './deliveries.js';
27
- import { migrateHumanRequestsState } from '../human/requests.js';
28
- import { existsSync, readFileSync, readdirSync, realpathSync } from 'node:fs';
29
- import { basename, join, resolve } from 'node:path';
30
- import { crtrHome, isSafeNodeId, nodesRoot, nodeMetaPath } from './paths.js';
31
- import { STATE_MIGRATIONS } from '../../migrations/registry.js';
32
- import { customExtensionPaths } from './extensions.js';
33
- import { readMetaObject, updateJsonFileDurably, withMetaLock, writeMetaObjectLocked } from './meta-file.js';
34
- // Schema as a forward-only migration list
35
- //
36
- // The schema is the migration list: one place a schema change is expressed,
37
- // one gate (`PRAGMA user_version`) that applies it. `migrate()` runs every
38
- // pending step in order and bumps `user_version` after each, so a fresh db and
39
- // the live fleet (all at `user_version 0`) converge on the same final shape.
40
- // Migrations are append-only and forward-only — never edit a shipped step. The
41
- // v36 body below is the sole corrective exception: v0.3.250 shipped a destructive
42
- // stale-row decision, so v36 is narrowed for databases still below its gate while
43
- // appended v37 repairs databases that already crossed it. Do not repeat this
44
- // exception; an appended migration is required unless it would run too late to
45
- // prevent destruction at an existing version boundary.
46
- /** v1 — the baseline tables + indexes. `IF NOT EXISTS` makes this a no-op on
47
- * any existing db (the live fleet already has these tables). */
48
- function baselineSchema(db) {
49
- db.exec(`
1
+ var J=Object.defineProperty;var i=(e,n)=>J(e,"name",{value:n,configurable:!0});import{importNodeSqlAuthority as Q}from"./node-sql-migration.js";import{migrateRecoveryWitnesses as V}from"./recovery.js";import{migrateMessagingState as Z}from"./deliveries.js";import{migrateHumanRequestsState as ee}from"../human/requests.js";import{existsSync as A,readFileSync as h,readdirSync as X,realpathSync as ne}from"node:fs";import{basename as te,join as y,resolve as H}from"node:path";import{crtrHome as oe,isSafeNodeId as ie,nodesRoot as S,nodeMetaPath as I}from"./paths.js";import{STATE_MIGRATIONS as re}from"../../migrations/registry.js";import{customExtensionPaths as se}from"./extensions.js";import{readMetaObject as P,updateJsonFileDurably as b,withMetaLock as Te,writeMetaObjectLocked as Ee}from"./meta-file.js";function ae(e){e.exec(`
50
2
  CREATE TABLE IF NOT EXISTS nodes (
51
3
  node_id TEXT PRIMARY KEY,
52
4
  name TEXT NOT NULL,
@@ -71,97 +23,7 @@ CREATE TABLE IF NOT EXISTS edges (
71
23
  CREATE INDEX IF NOT EXISTS idx_edges_to ON edges(type, to_id);
72
24
  CREATE INDEX IF NOT EXISTS idx_edges_from ON edges(type, from_id);
73
25
  CREATE INDEX IF NOT EXISTS idx_nodes_status ON nodes(status);
74
- `);
75
- }
76
- /** A table's current columns, used to make additive migrations safe to re-run
77
- * against a partially applied schema. Shared across every table this chain
78
- * alters in place (`nodes`, `consult_outbox`, `crons`) instead of each step
79
- * hand-rolling its own `PRAGMA table_info` + `Set` build. */
80
- function tableColumns(db, table) {
81
- return new Set(db.prepare(`PRAGMA table_info(${table})`).all().map((r) => r.name));
82
- }
83
- function addColumnIfMissing(db, columns, name, ddl) {
84
- if (columns.has(name))
85
- return;
86
- db.exec(ddl);
87
- columns.add(name);
88
- }
89
- /** `nodes`-table convenience alias — every existing call site names it this
90
- * way, and the table this chain adds columns to most is `nodes`. */
91
- function nodeColumns(db) {
92
- return tableColumns(db, 'nodes');
93
- }
94
- const addNodeColumnIfMissing = addColumnIfMissing;
95
- /** v2 — the additive runtime columns: `intent, pi_pid, window, tmux_session`.
96
- * `status` already lives in the baseline row, so it is NOT re-added here. All
97
- * four default to NULL; v3 backfills them. */
98
- function addRuntimeColumns(db) {
99
- const columns = nodeColumns(db);
100
- addNodeColumnIfMissing(db, columns, 'intent', `ALTER TABLE nodes ADD COLUMN intent TEXT;`);
101
- addNodeColumnIfMissing(db, columns, 'pi_pid', `ALTER TABLE nodes ADD COLUMN pi_pid INTEGER;`);
102
- addNodeColumnIfMissing(db, columns, 'window', `ALTER TABLE nodes ADD COLUMN window TEXT;`);
103
- addNodeColumnIfMissing(db, columns, 'tmux_session', `ALTER TABLE nodes ADD COLUMN tmux_session TEXT;`);
104
- }
105
- /** v3 — DATA backfill. The runtime fields
106
- * (`intent, pi_pid, window, tmux_session`) become authoritative in the row;
107
- * copy each existing node's values out of its meta.json into the row columns
108
- * once, so the version boundary loses no live state. `status` already mirrors
109
- * the row, so it is not re-copied.
110
- *
111
- * LAYERING NOTE — a sanctioned exception: a *data* migration must read
112
- * meta.json, which db.ts normally would not. Reading it
113
- * directly here — via paths.ts, a one-time, clearly-labeled boot-time data
114
- * migration — is the deliberate choice over splitting the `user_version`
115
- * counter across two modules. Idempotent and gated: it runs exactly once at the
116
- * v2→v3 boundary. An UPDATE for a node with no row yet hits 0 rows (harmless). */
117
- function backfillRuntime(db) {
118
- const root = nodesRoot();
119
- if (!existsSync(root))
120
- return;
121
- const upd = db.prepare('UPDATE nodes SET intent = ?, pi_pid = ?, "window" = ?, tmux_session = ? WHERE node_id = ?');
122
- for (const id of readdirSync(root)) {
123
- const p = nodeMetaPath(id);
124
- if (!existsSync(p))
125
- continue;
126
- let meta;
127
- try {
128
- meta = JSON.parse(readFileSync(p, 'utf8'));
129
- }
130
- catch {
131
- continue; // a single unreadable meta never aborts the migration
132
- }
133
- upd.run(meta['intent'] ?? null, meta['pi_pid'] ?? null, meta['window'] ?? null, meta['tmux_session'] ?? null, id);
134
- }
135
- }
136
- /** v4 — edges referential integrity (IRREVERSIBLE table rebuild). Rebuild the
137
- * `edges` table so `from_id`/`to_id` are FOREIGN KEYs to `nodes(node_id)` with
138
- * `ON DELETE CASCADE`: after this, deleting a node can NEVER orphan an edge —
139
- * the schema GCs them, so prune (and any future delete) doesn't have to. The
140
- * cargo-cult `PRAGMA foreign_keys = ON` (openDb) finally enforces something.
141
- *
142
- * GOTCHA — pre-existing orphan edges. Nothing ever deleted a node before this
143
- * phase, but manual dir removals / failed spawns can have left `edges` whose
144
- * endpoint has no `nodes` row. Copying those into the FK-constrained table
145
- * would violate the constraint, so the rebuild runs with `foreign_keys = OFF`
146
- * (it MUST be toggled in autocommit — a no-op inside a txn) and the
147
- * INSERT…SELECT FILTERS orphans: only edges whose BOTH endpoints have a row
148
- * survive. `PRAGMA foreign_key_check` then confirms the rebuilt table is clean,
149
- * and a row-count assertion guards that every NON-orphan edge is preserved.
150
- *
151
- * CRASH-SAFETY — the whole rebuild is one transaction. A throw ROLLs it back to
152
- * the pre-v4 state (the `edges_new` scratch table and all copies vanish) and
153
- * `user_version` stays at 3, so the next open re-runs v4 cleanly: no half-state.
154
- * Even a crash between COMMIT and the version bump is safe — re-running v4 over
155
- * an already-rebuilt (clean) `edges` is idempotent in effect. */
156
- function edgesForeignKeyCascade(db) {
157
- // Degenerate db with no `edges` table (a real db always has it — v1 created it
158
- // — but a hand-seeded fixture may not). Nothing to rebuild; create the
159
- // FK-shaped table fresh so the schema still converges, then we're done.
160
- const hasEdges = db
161
- .prepare("SELECT 1 FROM sqlite_master WHERE type = 'table' AND name = 'edges'")
162
- .get() !== undefined;
163
- if (!hasEdges) {
164
- db.exec(`
26
+ `)}i(ae,"baselineSchema");function w(e,n){return new Set(e.prepare(`PRAGMA table_info(${n})`).all().map(t=>t.name))}i(w,"tableColumns");function Y(e,n,t,o){n.has(t)||(e.exec(o),n.add(t))}i(Y,"addColumnIfMissing");function l(e){return w(e,"nodes")}i(l,"nodeColumns");const a=Y;function de(e){const n=l(e);a(e,n,"intent","ALTER TABLE nodes ADD COLUMN intent TEXT;"),a(e,n,"pi_pid","ALTER TABLE nodes ADD COLUMN pi_pid INTEGER;"),a(e,n,"window","ALTER TABLE nodes ADD COLUMN window TEXT;"),a(e,n,"tmux_session","ALTER TABLE nodes ADD COLUMN tmux_session TEXT;")}i(de,"addRuntimeColumns");function _e(e){const n=S();if(!A(n))return;const t=e.prepare('UPDATE nodes SET intent = ?, pi_pid = ?, "window" = ?, tmux_session = ? WHERE node_id = ?');for(const o of X(n)){const s=I(o);if(!A(s))continue;let T;try{T=JSON.parse(h(s,"utf8"))}catch{continue}t.run(T.intent??null,T.pi_pid??null,T.window??null,T.tmux_session??null,o)}}i(_e,"backfillRuntime");function ce(e){if(!(e.prepare("SELECT 1 FROM sqlite_master WHERE type = 'table' AND name = 'edges'").get()!==void 0)){e.exec(`
165
27
  CREATE TABLE edges (
166
28
  type TEXT NOT NULL,
167
29
  from_id TEXT NOT NULL,
@@ -174,21 +36,9 @@ CREATE TABLE edges (
174
36
  );
175
37
  CREATE INDEX IF NOT EXISTS idx_edges_to ON edges(type, to_id);
176
38
  CREATE INDEX IF NOT EXISTS idx_edges_from ON edges(type, from_id);
177
- `);
178
- return;
179
- }
180
- // FK enforcement must be toggled OUTSIDE a transaction (a no-op within one).
181
- db.exec('PRAGMA foreign_keys = OFF;');
182
- try {
183
- // Non-orphan edges that MUST survive the rebuild (both endpoints present).
184
- const expected = db
185
- .prepare(`SELECT COUNT(*) AS n FROM edges
39
+ `);return}e.exec("PRAGMA foreign_keys = OFF;");try{const t=e.prepare(`SELECT COUNT(*) AS n FROM edges
186
40
  WHERE from_id IN (SELECT node_id FROM nodes)
187
- AND to_id IN (SELECT node_id FROM nodes)`)
188
- .get().n;
189
- db.exec('BEGIN');
190
- try {
191
- db.exec(`
41
+ AND to_id IN (SELECT node_id FROM nodes)`).get().n;e.exec("BEGIN");try{e.exec(`
192
42
  CREATE TABLE edges_new (
193
43
  type TEXT NOT NULL,
194
44
  from_id TEXT NOT NULL,
@@ -207,74 +57,14 @@ DROP TABLE edges;
207
57
  ALTER TABLE edges_new RENAME TO edges;
208
58
  CREATE INDEX IF NOT EXISTS idx_edges_to ON edges(type, to_id);
209
59
  CREATE INDEX IF NOT EXISTS idx_edges_from ON edges(type, from_id);
210
- `);
211
- // Row-count assertion: every non-orphan edge preserved across the rebuild.
212
- const after = db.prepare('SELECT COUNT(*) AS n FROM edges').get().n;
213
- if (after !== expected) {
214
- throw new Error(`edges FK rebuild lost rows: expected ${expected} non-orphan edge(s), got ${after}`);
215
- }
216
- // Belt-and-suspenders: the rebuilt table must hold no FK violations (the
217
- // orphan filter above should guarantee this).
218
- const violations = db.prepare('PRAGMA foreign_key_check').all();
219
- if (violations.length > 0) {
220
- throw new Error(`edges FK rebuild left ${violations.length} foreign-key violation(s)`);
221
- }
222
- db.exec('COMMIT');
223
- }
224
- catch (e) {
225
- db.exec('ROLLBACK');
226
- throw e;
227
- }
228
- }
229
- finally {
230
- db.exec('PRAGMA foreign_keys = ON;');
231
- }
232
- }
233
- /** v5 — additive runtime column `pane`: LOCATION's authoritative handle, the
234
- * durable tmux `%pane_id` a node's pane is anchored on. Unlike the derived
235
- * `window`/`tmux_session` cache (v2), the pane id survives a user
236
- * `move-pane`/`join-pane`/`break-pane` and window renumbering, so a later step
237
- * reconciles window/session FROM it and uses pane-existence for liveness.
238
- * Defaults NULL — nothing reads it until the placement layer lands, so this
239
- * observes no behavior change. Additive, forward-only. */
240
- function addPaneColumn(db) {
241
- const columns = nodeColumns(db);
242
- addNodeColumnIfMissing(db, columns, 'pane', `ALTER TABLE nodes ADD COLUMN pane TEXT;`);
243
- }
244
- /** v6 — the `focuses` table: durable, PLURAL on-screen viewports, one row per
245
- * viewport (Q7 widens canvas.db from "topology" to "topology + focuses"). Each
246
- * row is anchored on the durable tmux `%pane_id`; `session` is a derived cache
247
- * reconciled from the pane; `node_id` is UNIQUE so a node occupies at most one
248
- * focus (Q5). The focuses table is the CANONICAL focus store — there is no
249
- * focus.ptr file and no dual-write bridge; placement writes focus rows directly. */
250
- function addFocusesTable(db) {
251
- db.exec(`
60
+ `);const o=e.prepare("SELECT COUNT(*) AS n FROM edges").get().n;if(o!==t)throw new Error(`edges FK rebuild lost rows: expected ${t} non-orphan edge(s), got ${o}`);const s=e.prepare("PRAGMA foreign_key_check").all();if(s.length>0)throw new Error(`edges FK rebuild left ${s.length} foreign-key violation(s)`);e.exec("COMMIT")}catch(o){throw e.exec("ROLLBACK"),o}}finally{e.exec("PRAGMA foreign_keys = ON;")}}i(ce,"edgesForeignKeyCascade");function Ne(e){const n=l(e);a(e,n,"pane","ALTER TABLE nodes ADD COLUMN pane TEXT;")}i(Ne,"addPaneColumn");function ue(e){e.exec(`
252
61
  CREATE TABLE IF NOT EXISTS focuses (
253
62
  focus_id TEXT PRIMARY KEY, -- stable internal id for the viewport
254
63
  pane TEXT, -- the durable %pane_id realizing the focus
255
64
  session TEXT, -- derived cache of the user session (reconciled from pane)
256
- node_id TEXT NOT NULL UNIQUE -- the node shown; UNIQUE → a node occupies <=1 focus
65
+ node_id TEXT NOT NULL UNIQUE -- the node shown; UNIQUE \u2192 a node occupies <=1 focus
257
66
  );
258
- `);
259
- }
260
- /** v7 — the `wakeups` table: durable store for scheduled wake-ups (the
261
- * scheduled-wakeups feature). One row per armed wake. `node_id` is the TARGET
262
- * and the node-anchored cancel anchor — it carries a `ON DELETE CASCADE` FK to
263
- * `nodes(node_id)` so a pruned/deleted node's node-anchored wakes are reaped in
264
- * the same transaction (mirroring the edges v4 cascade; works because
265
- * `PRAGMA foreign_keys = ON` is set at every open). NULL `node_id` = a
266
- * canvas-detached wake (deferred spawn / spawn-cron) that survives.
267
- *
268
- * `owner_id` is the ARMER, set on EVERY row, and is deliberately a PLAIN indexed
269
- * column with NO FK (design D1/D2): an FK on `owner_id` would cascade-drop a
270
- * crashed-then-pruned armer's detached cron, violating Invariant E. A detached
271
- * wake is never reaped by node-row cascade.
272
- *
273
- * `fire_at` is an ISO 8601 UTC string for the NEXT occurrence, so the per-tick
274
- * due query is a lexicographic `<=` compare. The partial unique index
275
- * `idx_wakeups_deadline` enforces ≤1 deadline per node. Additive, forward-only. */
276
- function appendWakeupsTable(db) {
277
- db.exec(`
67
+ `)}i(ue,"addFocusesTable");function le(e){e.exec(`
278
68
  CREATE TABLE IF NOT EXISTS wakeups (
279
69
  wakeup_id TEXT PRIMARY KEY,
280
70
  node_id TEXT, -- TARGET + node-anchored cancel anchor; NULL = canvas-detached
@@ -290,26 +80,7 @@ CREATE INDEX IF NOT EXISTS idx_wakeups_fire ON wakeups(fire_at);
290
80
  CREATE INDEX IF NOT EXISTS idx_wakeups_node ON wakeups(node_id); -- by-node cancel / list
291
81
  CREATE INDEX IF NOT EXISTS idx_wakeups_owner ON wakeups(owner_id); -- by-owner reap (ruling A)
292
82
  CREATE UNIQUE INDEX IF NOT EXISTS idx_wakeups_deadline ON wakeups(node_id) WHERE kind = 'deadline';
293
- `);
294
- }
295
- /** v9 — generalize the `wakeups` table (v7) into the `triggers` table (the
296
- * unified node-trigger-grammar substrate). The old `kind` axis (bare/noted/
297
- * deadline/spawn) splits into three orthogonal axes: `action` (what enacts:
298
- * 'msg'|'new') x `action_mode` (how: 'inbox_message'|'fresh_revive'|
299
- * 'deadline_message'|'node_birth') x `trigger_type` (when: 'at'|'every'|
300
- * 'when'|'until') — so a daemon-owned predicate (`--when`) trigger can live in
301
- * the same table as a clock trigger. Predicate-only columns (`when_script`
302
- * through `last_stderr`) are additive null/idle for every migrated clock row.
303
- *
304
- * Migration mapping, preserving every existing `wakeup_id` as `trigger_id`
305
- * (so an old wake's id stays cancelable): bare→fresh_revive, noted→
306
- * inbox_message, deadline→deadline_message (trigger_type='until'), spawn→
307
- * node_birth. `payload` JSON carries over unchanged — the old per-kind
308
- * payload shapes (plus SpawnChildOpts) map 1:1 onto the intermediate row, so
309
- * no JSON transform is needed. The `wakeups` table is then DROPPED — not kept
310
- * as a parallel table. Additive, forward-only. */
311
- function migrateWakeupsToTriggers(db) {
312
- db.exec(`
83
+ `)}i(le,"appendWakeupsTable");function Le(e){e.exec(`
313
84
  CREATE TABLE IF NOT EXISTS triggers (
314
85
  trigger_id TEXT PRIMARY KEY,
315
86
  owner_id TEXT NOT NULL,
@@ -360,134 +131,12 @@ SELECT
360
131
  FROM wakeups;
361
132
 
362
133
  DROP TABLE wakeups;
363
- `);
364
- }
365
- /** v8 — additive identity column `host_kind`: which HOST launches + supervises a
366
- * node — `'tmux'` (a pane) or `'broker'` (the headless in-process engine). It is
367
- * durable IDENTITY mirrored from meta.json like `cwd` (NOT runtime like `pane`),
368
- * so it survives an index rebuild via the `IDENTITY_KEYS`/`upsertRow` path.
369
- * Defaults NULL ⇒ `'tmux'` (every existing node is tmux-hosted); no data
370
- * backfill. Additive, forward-only. */
371
- function addHostKindColumn(db) {
372
- const columns = nodeColumns(db);
373
- addNodeColumnIfMissing(db, columns, 'host_kind', `ALTER TABLE nodes ADD COLUMN host_kind TEXT;`);
374
- }
375
- /** v10 — the `canvas_meta` key/value table: a single durable place for
376
- * small, cross-process canvas-wide scalars that aren't node rows. First user:
377
- * the boot marker (boot.ts), which records the last-seen kernel boot identity
378
- * so boot-liveness reconciliation is a single-writer SQLite transaction on
379
- * this row rather than a race-prone JSON file. Additive, forward-only. */
380
- function addCanvasMetaTable(db) {
381
- db.exec(`
134
+ `)}i(Le,"migrateWakeupsToTriggers");function pe(e){const n=l(e);a(e,n,"host_kind","ALTER TABLE nodes ADD COLUMN host_kind TEXT;")}i(pe,"addHostKindColumn");function Oe(e){e.exec(`
382
135
  CREATE TABLE IF NOT EXISTS canvas_meta (
383
136
  key TEXT PRIMARY KEY,
384
137
  value TEXT NOT NULL
385
138
  );
386
- `);
387
- }
388
- /** v11 — additive identity column `profile_id`: the profile-directory id
389
- * (`<slug>-<id>`) a node runs under, chosen once at spawn (inherited from the
390
- * spawner, or `--profile`). Durable IDENTITY mirrored from meta.json like
391
- * `cwd`/`host_kind` (NOT runtime like `pane`), so it survives an index rebuild
392
- * via the `IDENTITY_KEYS`/`upsertRow` path. Defaults NULL for historical
393
- * root/no-profile rows; new root conversations use the stable root profile
394
- * id instead. No data backfill. Additive, forward-only. */
395
- function addProfileIdColumn(db) {
396
- const columns = nodeColumns(db);
397
- addNodeColumnIfMissing(db, columns, 'profile_id', `ALTER TABLE nodes ADD COLUMN profile_id TEXT;`);
398
- }
399
- /** v12 — additive runtime column `pi_pid_identity`: the LAUNCH-time process-
400
- * identity fingerprint (`pid.ts`'s `composeIdentity`) recorded alongside
401
- * `pi_pid` (v2) by `recordPid`, so `headlessBrokerHost.teardown()` can refuse
402
- * to signal a `pi_pid` the OS has since recycled for an unrelated process
403
- * (see `NodeRuntime.pi_pid_identity`).
404
- * Defaults NULL ⇒ no baseline ⇒ the guard fails open, exactly like a node
405
- * booted before this column existed. No data backfill: an existing `pi_pid`
406
- * with no recorded identity simply has no launch-time baseline to compare
407
- * against. Additive, forward-only. */
408
- function addPidIdentityColumn(db) {
409
- const columns = nodeColumns(db);
410
- addNodeColumnIfMissing(db, columns, 'pi_pid_identity', `ALTER TABLE nodes ADD COLUMN pi_pid_identity TEXT;`);
411
- }
412
- /** v13 — mutable controller-message wait state. It belongs with runtime state,
413
- * not meta identity: both the waiting node and an incoming sender can settle it. */
414
- function addMessageWaitColumn(db) {
415
- const columns = nodeColumns(db);
416
- addNodeColumnIfMissing(db, columns, 'waiting_for', `ALTER TABLE nodes ADD COLUMN waiting_for TEXT;`);
417
- }
418
- /** v14 — canonical final identity. Existing done rows receive their newest valid
419
- * final report once; runtime never infers canonical state from report files. */
420
- function addCanonicalFinalColumns(db) {
421
- const columns = nodeColumns(db);
422
- // Metadata-only migration harnesses can legitimately advance user_version on
423
- // an otherwise empty database. There is no node index to repair in that case.
424
- if (columns.size === 0)
425
- return;
426
- addNodeColumnIfMissing(db, columns, 'final_report', `ALTER TABLE nodes ADD COLUMN final_report TEXT;`);
427
- addNodeColumnIfMissing(db, columns, 'finalized_at', `ALTER TABLE nodes ADD COLUMN finalized_at TEXT;`);
428
- const rows = db.prepare("SELECT node_id FROM nodes WHERE status = 'done' AND final_report IS NULL").all();
429
- const update = db.prepare('UPDATE nodes SET final_report = ?, finalized_at = ? WHERE node_id = ? AND final_report IS NULL');
430
- for (const { node_id } of rows) {
431
- const dir = join(nodesRoot(), node_id, 'reports');
432
- if (!existsSync(dir))
433
- continue;
434
- let winner = null;
435
- for (const name of readdirSync(dir)) {
436
- if (!name.endsWith('.md'))
437
- continue;
438
- try {
439
- const raw = readFileSync(join(dir, name), 'utf8');
440
- const match = /^---\nnode: [^\n]+\nkind: final\nts: ([^\n]+)\n---\n/.exec(raw);
441
- if (match === null || Number.isNaN(Date.parse(match[1])))
442
- continue;
443
- const candidate = { name, ts: match[1] };
444
- if (winner === null || candidate.ts > winner.ts || (candidate.ts === winner.ts && candidate.name > winner.name))
445
- winner = candidate;
446
- }
447
- catch { /* malformed historical reports are not canonical */ }
448
- }
449
- if (winner !== null)
450
- update.run(winner.name, winner.ts, node_id);
451
- }
452
- }
453
- /** v15 — canonicalize persisted launch metadata after a retired generation-root
454
- * experiment. Canvas hooks are launch-owned; retain every genuine custom extra. */
455
- function normalizePersistedLaunchExtensions(_db) {
456
- const root = nodesRoot();
457
- if (!existsSync(root))
458
- return;
459
- for (const id of readdirSync(root)) {
460
- const path = nodeMetaPath(id);
461
- if (!existsSync(path))
462
- continue;
463
- updateJsonFileDurably(path, (meta) => {
464
- const launch = meta['launch'];
465
- if (typeof launch !== 'object' || launch === null || Array.isArray(launch))
466
- return false;
467
- const extensions = launch.extensions;
468
- if (!Array.isArray(extensions) || !extensions.every((value) => typeof value === 'string'))
469
- return false;
470
- const custom = customExtensionPaths(extensions);
471
- if (custom.length === extensions.length)
472
- return false;
473
- launch.extensions = custom;
474
- return true;
475
- });
476
- }
477
- }
478
- /** v17 — monotonically identifies each explicit wait arm. Delivery settlement
479
- * uses this watermark as well as the controller identity. */
480
- function addMessageWaitGenerationColumn(db) {
481
- const columns = nodeColumns(db);
482
- addNodeColumnIfMissing(db, columns, 'waiting_for_generation', `ALTER TABLE nodes ADD COLUMN waiting_for_generation INTEGER NOT NULL DEFAULT 0;`);
483
- }
484
- /** v18 — create the historical `consult_outbox` table. The old schema stays
485
- * replayable for existing databases until its later migration removes it.
486
- * No current user-facing flow creates rows. Its remaining diagnostics and
487
- * retention readers keep armed/pending legacy rows from losing their node
488
- * before startup or crash reconciliation terminalizes those rows. */
489
- function addHumanWorkOutboxTable(db) {
490
- db.exec(`
139
+ `)}i(Oe,"addCanvasMetaTable");function Ae(e){const n=l(e);a(e,n,"profile_id","ALTER TABLE nodes ADD COLUMN profile_id TEXT;")}i(Ae,"addProfileIdColumn");function fe(e){const n=l(e);a(e,n,"pi_pid_identity","ALTER TABLE nodes ADD COLUMN pi_pid_identity TEXT;")}i(fe,"addPidIdentityColumn");function Re(e){const n=l(e);a(e,n,"waiting_for","ALTER TABLE nodes ADD COLUMN waiting_for TEXT;")}i(Re,"addMessageWaitColumn");function $(e){const n=l(e);if(n.size===0)return;a(e,n,"final_report","ALTER TABLE nodes ADD COLUMN final_report TEXT;"),a(e,n,"finalized_at","ALTER TABLE nodes ADD COLUMN finalized_at TEXT;");const t=e.prepare("SELECT node_id FROM nodes WHERE status = 'done' AND final_report IS NULL").all(),o=e.prepare("UPDATE nodes SET final_report = ?, finalized_at = ? WHERE node_id = ? AND final_report IS NULL");for(const{node_id:s}of t){const T=y(S(),s,"reports");if(!A(T))continue;let r=null;for(const E of X(T))if(E.endsWith(".md"))try{const d=h(y(T,E),"utf8"),_=/^---\nnode: [^\n]+\nkind: final\nts: ([^\n]+)\n---\n/.exec(d);if(_===null||Number.isNaN(Date.parse(_[1])))continue;const c={name:E,ts:_[1]};(r===null||c.ts>r.ts||c.ts===r.ts&&c.name>r.name)&&(r=c)}catch{}r!==null&&o.run(r.name,r.ts,s)}}i($,"addCanonicalFinalColumns");function me(e){const n=S();if(A(n))for(const t of X(n)){const o=I(t);A(o)&&b(o,s=>{const T=s.launch;if(typeof T!="object"||T===null||Array.isArray(T))return!1;const r=T.extensions;if(!Array.isArray(r)||!r.every(d=>typeof d=="string"))return!1;const E=se(r);return E.length===r.length?!1:(T.extensions=E,!0)})}}i(me,"normalizePersistedLaunchExtensions");function Ie(e){const n=l(e);a(e,n,"waiting_for_generation","ALTER TABLE nodes ADD COLUMN waiting_for_generation INTEGER NOT NULL DEFAULT 0;")}i(Ie,"addMessageWaitGenerationColumn");function Xe(e){e.exec(`
491
140
  CREATE TABLE IF NOT EXISTS consult_outbox (
492
141
  node_id TEXT PRIMARY KEY, -- legacy work node id
493
142
  dir TEXT NOT NULL, -- legacy ticket directory
@@ -501,56 +150,15 @@ CREATE INDEX IF NOT EXISTS idx_consult_outbox_status ON consult_outbox(status);
501
150
  CREATE INDEX IF NOT EXISTS idx_consult_outbox_dir ON consult_outbox(dir);
502
151
  CREATE INDEX IF NOT EXISTS idx_consult_outbox_dir_request_status ON consult_outbox(dir, request_id, status);
503
152
  CREATE INDEX IF NOT EXISTS idx_consult_outbox_dir_status ON consult_outbox(dir, status);
504
- `);
505
- }
506
- /** v19 — generalize the physical `consult_outbox` ABI into human work without
507
- * changing its table name. Existing rows and old literal follow-up inserts gain
508
- * `follow_up` by default; Visual reserves namespaced statuses so old
509
- * `armed`/`pending` reconcilers cannot select it. */
510
- function addHumanWorkColumns(db) {
511
- const columns = tableColumns(db, 'consult_outbox');
512
- const add = (name, ddl) => addColumnIfMissing(db, columns, name, ddl);
513
- add('work_kind', "ALTER TABLE consult_outbox ADD COLUMN work_kind TEXT NOT NULL DEFAULT 'follow_up';");
514
- add('interaction_id', 'ALTER TABLE consult_outbox ADD COLUMN interaction_id TEXT;');
515
- add('generation_id', 'ALTER TABLE consult_outbox ADD COLUMN generation_id TEXT;');
516
- add('interaction_snapshot', 'ALTER TABLE consult_outbox ADD COLUMN interaction_snapshot TEXT;');
517
- add('handler_command', 'ALTER TABLE consult_outbox ADD COLUMN handler_command TEXT;');
518
- add('handler_args_json', 'ALTER TABLE consult_outbox ADD COLUMN handler_args_json TEXT;');
519
- add('claim_token', 'ALTER TABLE consult_outbox ADD COLUMN claim_token TEXT;');
520
- db.exec(`
153
+ `)}i(Xe,"addHumanWorkOutboxTable");function Se(e){const n=w(e,"consult_outbox"),t=i((o,s)=>Y(e,n,o,s),"add");t("work_kind","ALTER TABLE consult_outbox ADD COLUMN work_kind TEXT NOT NULL DEFAULT 'follow_up';"),t("interaction_id","ALTER TABLE consult_outbox ADD COLUMN interaction_id TEXT;"),t("generation_id","ALTER TABLE consult_outbox ADD COLUMN generation_id TEXT;"),t("interaction_snapshot","ALTER TABLE consult_outbox ADD COLUMN interaction_snapshot TEXT;"),t("handler_command","ALTER TABLE consult_outbox ADD COLUMN handler_command TEXT;"),t("handler_args_json","ALTER TABLE consult_outbox ADD COLUMN handler_args_json TEXT;"),t("claim_token","ALTER TABLE consult_outbox ADD COLUMN claim_token TEXT;"),e.exec(`
521
154
  CREATE INDEX IF NOT EXISTS idx_consult_outbox_human_work_status ON consult_outbox(work_kind, status);
522
155
  CREATE INDEX IF NOT EXISTS idx_consult_outbox_human_work_dir_status ON consult_outbox(dir, work_kind, status);
523
156
  CREATE INDEX IF NOT EXISTS idx_consult_outbox_human_work_request_status ON consult_outbox(dir, request_id, work_kind, status);
524
157
  CREATE UNIQUE INDEX IF NOT EXISTS idx_consult_outbox_visual_request ON consult_outbox(dir, request_id, work_kind) WHERE work_kind = 'visual';
525
- `);
526
- }
527
- /** v20 — index `nodes(parent)` and `nodes(created)`. `listNodes()`'s
528
- * `ORDER BY created` and the `children = rows.filter(r => r.parent === id)`
529
- * child lookup (`daemon/api/handlers/nodes.ts`'s `edgesFor`) were both
530
- * full-table scans under the daemon's single event loop; a live fleet's
531
- * `GET /v1/nodes/:id` measured >15s under concurrent-viewer load. Additive,
532
- * forward-only — `IF NOT EXISTS` makes re-running a no-op. */
533
- function addNodeParentCreatedIndexes(db) {
534
- db.exec(`
158
+ `)}i(Se,"addHumanWorkColumns");function Ue(e){e.exec(`
535
159
  CREATE INDEX IF NOT EXISTS idx_nodes_parent ON nodes(parent);
536
160
  CREATE INDEX IF NOT EXISTS idx_nodes_created ON nodes(created);
537
- `);
538
- }
539
- /** v21 — the `crons` + `cron_runs` tables. One scheduling primitive: run this
540
- * bash, then. Key contracts pinned by the spec:
541
- * - `created_by` is provenance ONLY — no FK, never cascades; a lifelong job
542
- * is not hostage to the window that typed it.
543
- * - `anchor_node` is the OPT-IN node coupling, carrying the one FK
544
- * (ON DELETE CASCADE); NULL = outlives every node on the canvas.
545
- * - the partial unique index `idx_crons_deadline` is the ≤1-deadline-per-node
546
- * backstop for the future `node wait deadline` sugar (cancel_on_wake rows).
547
- * - execution context (cwd/env/profile) is SNAPSHOTTED at arm time, never
548
- * resolved at run time.
549
- * - `cron_runs` is a bounded ring (last 20 per cron, pruned by the DAO's
550
- * recordCronRun).
551
- * Additive and forward-only. */
552
- function addCronsTables(db) {
553
- db.exec(`
161
+ `)}i(Ue,"addNodeParentCreatedIndexes");function ge(e){e.exec(`
554
162
  CREATE TABLE IF NOT EXISTS crons (
555
163
  cron_id TEXT PRIMARY KEY,
556
164
  name TEXT NOT NULL, -- agent-legible label; how it shows in list
@@ -605,411 +213,38 @@ CREATE TABLE IF NOT EXISTS cron_runs ( -- bounded ring, last 20 p
605
213
  FOREIGN KEY (cron_id) REFERENCES crons(cron_id) ON DELETE CASCADE
606
214
  );
607
215
  CREATE INDEX IF NOT EXISTS idx_cron_runs_cron ON cron_runs(cron_id, started);
608
- `);
609
- }
610
- function shellSingleQuote(value) {
611
- return `'${value.replace(/'/g, `'"'"'`)}'`;
612
- }
613
- function uniqueHeredocDelimiter(body, stem) {
614
- let suffix = 0;
615
- while (true) {
616
- const delimiter = `${stem}_${suffix}`;
617
- if (!body.split('\n').includes(delimiter))
618
- return delimiter;
619
- suffix++;
620
- }
621
- }
622
- function heredocCommand(command, body, stem) {
623
- const delimiter = uniqueHeredocDelimiter(body, stem);
624
- return `${command} <<'${delimiter}'\n${body}\n${delimiter}`;
625
- }
626
- /** `payload` was a NULLABLE text column, so NULL, non-string, and legacy or
627
- * hand-edited JSON are all shapes the retired schema declared legal. A schema
628
- * migration must never fail on data shape, so anything unreadable degrades to
629
- * an empty payload; the per-key readers below then decide whether what is left
630
- * is enough to convert the row. */
631
- function migrationPayload(raw) {
632
- if (typeof raw !== 'string')
633
- return {};
634
- try {
635
- const parsed = JSON.parse(raw);
636
- if (typeof parsed !== 'object' || parsed === null || Array.isArray(parsed))
637
- return {};
638
- return parsed;
639
- }
640
- catch {
641
- return {};
642
- }
643
- }
644
- function requiredString(payload, key, triggerId) {
645
- const value = payload[key];
646
- if (typeof value !== 'string' || value.trim() === '') {
647
- throw new Error(`trigger ${triggerId} payload requires non-empty ${key}`);
648
- }
649
- return value;
650
- }
651
- function optionalString(payload, key) {
652
- const value = payload[key];
653
- return typeof value === 'string' && value.trim() !== '' ? value : undefined;
654
- }
655
- /** The same reader over a `triggers` ROW rather than its payload: returns the
656
- * column when it holds a usable string, `undefined` otherwise. */
657
- function optionalColumn(row, key) {
658
- const value = row[key];
659
- return typeof value === 'string' && value.trim() !== '' ? value : undefined;
660
- }
661
- function migratedMessageCommand(target, tier, body, triggerId) {
662
- return heredocCommand(`crtr node message send --to ${shellSingleQuote(target)} --tier ${shellSingleQuote(tier)}`, body, `CRTR_MIGRATED_${triggerId.replace(/[^A-Za-z0-9]/g, '_')}`);
663
- }
664
- /** A body-less predicate message: the retired daemon filled the body from the
665
- * gate's stdout at fire time (`p.body ?? outcome.stdout`), so the migrated
666
- * script pipes the captured gate output into the send. */
667
- function migratedGateStdoutMessageCommand(target, tier) {
668
- return `printf '%s\\n' "$CRTR_GATE_STDOUT" | crtr node message send --to ${shellSingleQuote(target)} --tier ${shellSingleQuote(tier)}`;
669
- }
670
- function migratedSpawnCommand(payload, triggerId) {
671
- const flags = [`crtr node new --kind ${shellSingleQuote(requiredString(payload, 'kind', triggerId))}`];
672
- const strings = [
673
- ['mode', 'mode'],
674
- ['cwd', 'cwd'],
675
- ['name', 'name'],
676
- ['parent', 'parent'],
677
- ['worktreeBase', 'worktree'],
678
- ['forkFrom', 'fork-from'],
679
- ['model', 'model'],
680
- ['profile', 'profile'],
681
- ['situationalContext', 'situational-context'],
682
- ];
683
- for (const [key, flag] of strings) {
684
- const value = optionalString(payload, key);
685
- if (value !== undefined)
686
- flags.push(`--${flag} ${shellSingleQuote(value)}`);
687
- }
688
- if (payload['root'] === true)
689
- flags.push('--root');
690
- const prompt = requiredString(payload, 'prompt', triggerId);
691
- return heredocCommand(flags.join(' '), prompt, `CRTR_MIGRATED_${triggerId.replace(/[^A-Za-z0-9]/g, '_')}`);
692
- }
693
- /** The `canvas_meta` key holding the v22 skip ledger: a JSON array of
694
- * `{ trigger_id, reason }` for every retired schedule the migration could not
695
- * express as a cron. Written only when at least one row is skipped. */
696
- const V22_SKIPPED_META_KEY = 'migration.v22.skipped';
697
- /** The execution-context cwd for a schedule whose armer is gone. `owner_id`
698
- * carries NO foreign key by design (see v7), so a crashed-then-pruned armer's
699
- * detached schedule is an EXPECTED row, not a corrupt one — it must still
700
- * convert. Falls back to the oldest root node's cwd (the ambient canvas root),
701
- * then to this process's cwd. */
702
- function ambientMigrationCwd(db) {
703
- const root = db
704
- .prepare('SELECT cwd FROM nodes WHERE parent IS NULL ORDER BY created LIMIT 1')
705
- .get();
706
- return (root !== undefined ? optionalColumn(root, 'cwd') : undefined) ?? process.cwd();
707
- }
708
- /** Best-effort reap of in-flight predicate evaluations before the table that
709
- * records them is dropped. The retired cancel path killed the evaluation's
710
- * process GROUP; without this the migration would orphan a running gate
711
- * script with nothing left on disk that names it. */
712
- function reapRunningPredicateEvaluations(db) {
713
- let running;
714
- try {
715
- running = db
716
- .prepare("SELECT eval_pid FROM triggers WHERE eval_state = 'running' AND eval_pid IS NOT NULL")
717
- .all();
718
- }
719
- catch {
720
- return; // a drifted table shape has no evaluations we can name; never fatal
721
- }
722
- for (const row of running) {
723
- const pid = row['eval_pid'];
724
- if (typeof pid !== 'number' || !Number.isInteger(pid) || pid <= 1)
725
- continue;
726
- try {
727
- process.kill(-pid, 'SIGTERM');
728
- }
729
- catch {
730
- /* the evaluation already exited, or the group is gone — nothing to reap */
731
- }
732
- }
733
- }
734
- /** v22 — migrate each scheduled action into a shell cron, preserving its id and
735
- * execution context, then remove the superseded table.
736
- *
737
- * SKIP-AND-RECORD, never throw. A migration that hard-fails on data shape would
738
- * block daemon startup. Rows the retired schema declared legal but this step
739
- * cannot express (unknown action/timing pairs, a missing fire time, drifted
740
- * JSON) are skipped, named in the `canvas_meta` ledger under
741
- * `migration.v22.skipped`, and warned about — the schema always advances.
742
- * `INSERT OR REPLACE` makes a re-run over already-converted ids converge rather
743
- * than collide on the `cron_id` primary key. */
744
- function migrateTriggersToCrons(db) {
745
- const skipped = [];
746
- // A db already wedged by an interrupted pre-atomicity run (crons committed,
747
- // the table dropped, `user_version` still 21) re-runs this step with nothing
748
- // left to convert; it must advance, not throw.
749
- const hasTriggers = db
750
- .prepare("SELECT 1 FROM sqlite_master WHERE type = 'table' AND name = 'triggers'")
751
- .get() !== undefined;
752
- if (hasTriggers)
753
- reapRunningPredicateEvaluations(db);
754
- let rows = [];
755
- if (hasTriggers) {
756
- try {
757
- rows = db.prepare('SELECT * FROM triggers ORDER BY created, trigger_id').all();
758
- }
759
- catch (err) {
760
- // A column-drifted table (no `created`/`trigger_id`) must not brick every
761
- // open either: record that its rows were unreadable and advance.
762
- skipped.push({
763
- trigger_id: '<unreadable table>',
764
- reason: `triggers table could not be read: ${err instanceof Error ? err.message : String(err)}`,
765
- });
766
- }
767
- }
768
- const fallbackCwd = ambientMigrationCwd(db);
769
- const insert = db.prepare(`
216
+ `)}i(ge,"addCronsTables");function f(e){return`'${e.replace(/'/g,`'"'"'`)}'`}i(f,"shellSingleQuote");function Ce(e,n){let t=0;for(;;){const o=`${n}_${t}`;if(!e.split(`
217
+ `).includes(o))return o;t++}}i(Ce,"uniqueHeredocDelimiter");function W(e,n,t){const o=Ce(n,t);return`${e} <<'${o}'
218
+ ${n}
219
+ ${o}`}i(W,"heredocCommand");function De(e){if(typeof e!="string")return{};try{const n=JSON.parse(e);return typeof n!="object"||n===null||Array.isArray(n)?{}:n}catch{return{}}}i(De,"migrationPayload");function L(e,n,t){const o=e[n];if(typeof o!="string"||o.trim()==="")throw new Error(`trigger ${t} payload requires non-empty ${n}`);return o}i(L,"requiredString");function U(e,n){const t=e[n];return typeof t=="string"&&t.trim()!==""?t:void 0}i(U,"optionalString");function R(e,n){const t=e[n];return typeof t=="string"&&t.trim()!==""?t:void 0}i(R,"optionalColumn");function K(e,n,t,o){return W(`crtr node message send --to ${f(e)} --tier ${f(n)}`,t,`CRTR_MIGRATED_${o.replace(/[^A-Za-z0-9]/g,"_")}`)}i(K,"migratedMessageCommand");function he(e,n){return`printf '%s\\n' "$CRTR_GATE_STDOUT" | crtr node message send --to ${f(e)} --tier ${f(n)}`}i(he,"migratedGateStdoutMessageCommand");function we(e,n){const t=[`crtr node new --kind ${f(L(e,"kind",n))}`],o=[["mode","mode"],["cwd","cwd"],["name","name"],["parent","parent"],["worktreeBase","worktree"],["forkFrom","fork-from"],["model","model"],["profile","profile"],["situationalContext","situational-context"]];for(const[T,r]of o){const E=U(e,T);E!==void 0&&t.push(`--${r} ${f(E)}`)}e.root===!0&&t.push("--root");const s=L(e,"prompt",n);return W(t.join(" "),s,`CRTR_MIGRATED_${n.replace(/[^A-Za-z0-9]/g,"_")}`)}i(we,"migratedSpawnCommand");const q="migration.v22.skipped";function xe(e){const n=e.prepare("SELECT cwd FROM nodes WHERE parent IS NULL ORDER BY created LIMIT 1").get();return(n!==void 0?R(n,"cwd"):void 0)??process.cwd()}i(xe,"ambientMigrationCwd");function ve(e){let n;try{n=e.prepare("SELECT eval_pid FROM triggers WHERE eval_state = 'running' AND eval_pid IS NOT NULL").all()}catch{return}for(const t of n){const o=t.eval_pid;if(!(typeof o!="number"||!Number.isInteger(o)||o<=1))try{process.kill(-o,"SIGTERM")}catch{}}}i(ve,"reapRunningPredicateEvaluations");function Fe(e){const n=[],t=e.prepare("SELECT 1 FROM sqlite_master WHERE type = 'table' AND name = 'triggers'").get()!==void 0;t&&ve(e);let o=[];if(t)try{o=e.prepare("SELECT * FROM triggers ORDER BY created, trigger_id").all()}catch(r){n.push({trigger_id:"<unreadable table>",reason:`triggers table could not be read: ${r instanceof Error?r.message:String(r)}`})}const s=xe(e),T=e.prepare(`
770
220
  INSERT OR REPLACE INTO crons (
771
221
  cron_id, name, created_by, command, fire_at, recur, tz, expires_at,
772
222
  anchor_node, cancel_on_wake, cwd, env_json, profile, scope,
773
223
  run_timeout_s, overlap, on_output, sink, tier, created, updated
774
- ) VALUES (?, ?, ?, ?, ?, ?, NULL, ?, ?, ?, ?, NULL, ?, 'profile', ?, 'skip', 'on-failure', '{}', ?, ?, ?)`);
775
- for (const row of rows) {
776
- const triggerId = optionalColumn(row, 'trigger_id');
777
- if (triggerId === undefined) {
778
- skipped.push({ trigger_id: '<unidentified row>', reason: 'row carries no trigger_id' });
779
- continue;
780
- }
781
- try {
782
- convertTriggerRow(db, insert, row, triggerId, fallbackCwd);
783
- }
784
- catch (err) {
785
- skipped.push({ trigger_id: triggerId, reason: err instanceof Error ? err.message : String(err) });
786
- }
787
- }
788
- if (skipped.length > 0) {
789
- db.prepare('INSERT INTO canvas_meta (key, value) VALUES (?, ?) ON CONFLICT(key) DO UPDATE SET value = excluded.value').run(V22_SKIPPED_META_KEY, JSON.stringify(skipped));
790
- console.warn(`[canvas migration v22] ${skipped.length} retired schedule(s) could not be converted to crons and were dropped; ` +
791
- `see canvas_meta['${V22_SKIPPED_META_KEY}']: ` +
792
- skipped.map((entry) => `${entry.trigger_id} (${entry.reason})`).join('; '));
793
- }
794
- db.exec(`
224
+ ) VALUES (?, ?, ?, ?, ?, ?, NULL, ?, ?, ?, ?, NULL, ?, 'profile', ?, 'skip', 'on-failure', '{}', ?, ?, ?)`);for(const r of o){const E=R(r,"trigger_id");if(E===void 0){n.push({trigger_id:"<unidentified row>",reason:"row carries no trigger_id"});continue}try{ye(e,T,r,E,s)}catch(d){n.push({trigger_id:E,reason:d instanceof Error?d.message:String(d)})}}n.length>0&&(e.prepare("INSERT INTO canvas_meta (key, value) VALUES (?, ?) ON CONFLICT(key) DO UPDATE SET value = excluded.value").run(q,JSON.stringify(n)),console.warn(`[canvas migration v22] ${n.length} retired schedule(s) could not be converted to crons and were dropped; see canvas_meta['${q}']: `+n.map(r=>`${r.trigger_id} (${r.reason})`).join("; "))),e.exec(`
795
225
  DROP INDEX IF EXISTS idx_triggers_fire;
796
226
  DROP INDEX IF EXISTS idx_triggers_node;
797
227
  DROP INDEX IF EXISTS idx_triggers_owner;
798
228
  DROP INDEX IF EXISTS idx_triggers_eval;
799
229
  DROP INDEX IF EXISTS idx_triggers_deadline;
800
230
  DROP TABLE IF EXISTS triggers;
801
- `);
802
- }
803
- /** Convert ONE retired schedule row into a cron row. Throws only when the row
804
- * cannot be expressed as a cron at all; the caller turns that into a recorded
805
- * skip so the schema still advances. */
806
- function convertTriggerRow(db, insert, row, triggerId, fallbackCwd) {
807
- const ownerId = requiredString(row, 'owner_id', triggerId);
808
- // A pruned armer is expected, not corrupt (no FK on `owner_id`, by design):
809
- // keep the schedule and snapshot the ambient root cwd instead of its armer's.
810
- const owner = db.prepare('SELECT cwd, profile_id FROM nodes WHERE node_id = ?').get(ownerId);
811
- const cwd = (owner === undefined ? undefined : optionalColumn(owner, 'cwd')) ?? fallbackCwd;
812
- const profile = owner === undefined ? null : optionalColumn(owner, 'profile_id') ?? null;
813
- const nodeId = optionalColumn(row, 'node_id') ?? null;
814
- const action = requiredString(row, 'action', triggerId);
815
- const actionMode = requiredString(row, 'action_mode', triggerId);
816
- const triggerType = requiredString(row, 'trigger_type', triggerId);
817
- const payload = migrationPayload(row['payload']);
818
- const created = optionalColumn(row, 'created') ?? new Date().toISOString();
819
- const tier = actionMode === 'deadline_message' ? 'urgent' : optionalString(payload, 'tier') ?? 'normal';
820
- const label = optionalString(payload, 'label');
821
- let command;
822
- let name;
823
- // A `--when` schedule could legally omit its body: the retired daemon filled
824
- // it from the gate's stdout at fire time. Such a row pipes the captured gate
825
- // output into the send instead of carrying a heredoc.
826
- let bodyFromGate = false;
827
- if (action === 'msg' && (actionMode === 'inbox_message' || actionMode === 'deadline_message')) {
828
- if (nodeId === null)
829
- throw new Error('has no message target');
830
- const body = optionalString(payload, 'body');
831
- if (body !== undefined) {
832
- command = migratedMessageCommand(nodeId, tier, body, triggerId);
833
- }
834
- else if (triggerType === 'when') {
835
- bodyFromGate = true;
836
- command = migratedGateStdoutMessageCommand(nodeId, tier);
837
- }
838
- else {
839
- // Not expressible from a gate: synthesize the most informative body the
840
- // row still holds rather than losing the enactment.
841
- command = migratedMessageCommand(nodeId, tier, label ?? 'Scheduled message (no body was recorded when this schedule was armed).', triggerId);
842
- }
843
- name = label ?? (actionMode === 'deadline_message' ? 'deadline' : 'scheduled message');
844
- }
845
- else if (action === 'msg' && actionMode === 'fresh_revive') {
846
- if (nodeId === null)
847
- throw new Error('has no revive target');
848
- command = `crtr node lifecycle revive ${shellSingleQuote(nodeId)} --fresh`;
849
- name = label ?? 'scheduled fresh revive';
850
- }
851
- else if (action === 'new' && actionMode === 'node_birth') {
852
- command = migratedSpawnCommand(payload, triggerId);
853
- name = optionalString(payload, 'name') ?? `scheduled ${requiredString(payload, 'kind', triggerId)} node`;
854
- }
855
- else {
856
- throw new Error(`has unsupported action ${action}/${actionMode}`);
857
- }
858
- let fireAt;
859
- let recur;
860
- let expiresAt = null;
861
- if (triggerType === 'when') {
862
- fireAt = requiredString(row, 'next_eval_at', triggerId);
863
- // A when-row with no evaluation cadence would silently become a ONE-SHOT
864
- // gate that evaporates on its first unsatisfied check; skip-and-record it.
865
- recur = requiredString(row, 'eval_every', triggerId);
866
- expiresAt = optionalColumn(row, 'timeout_at') ?? null;
867
- const gate = requiredString(row, 'when_script', triggerId);
868
- const open = bodyFromGate ? `if ! CRTR_GATE_STDOUT="$(\n${gate}\n)"; then` : `if ! (\n${gate}\n); then`;
869
- // `&&`, not a newline: the run's exit status must be the ACTION's, so a
870
- // failed enactment escalates through the cron's on-failure path and leaves
871
- // the cron armed instead of silently self-cancelling on a lost message.
872
- // The action is BRACE-GROUPED because it may be heredoc-shaped: a `&&`
873
- // appended straight onto it would land on the heredoc's closing delimiter
874
- // line, which then never terminates the document.
875
- command = `${open}\n exit 0\nfi\n{\n${command}\n} && crtr cron cancel "$CRTR_CRON_ID"`;
876
- }
877
- else if (triggerType === 'at' || triggerType === 'every' || triggerType === 'until') {
878
- fireAt = requiredString(row, 'fire_at', triggerId);
879
- recur = triggerType === 'every' ? requiredString(row, 'recur', triggerId) : null;
880
- }
881
- else {
882
- throw new Error(`has unknown timing type ${triggerType}`);
883
- }
884
- // `INSERT OR REPLACE` (the re-run convergence for a repeated `cron_id`) would
885
- // ALSO silently evict a conflicting row on the ≤1-deadline-per-node partial
886
- // index. Only drifted data can produce that shape, and it must be recorded,
887
- // not resolved in silence: keep the earlier deadline, skip this one.
888
- if (actionMode === 'deadline_message' && nodeId !== null) {
889
- const rival = db
890
- .prepare('SELECT cron_id FROM crons WHERE anchor_node = ? AND cancel_on_wake = 1 AND cron_id <> ?')
891
- .get(nodeId, triggerId);
892
- if (rival !== undefined) {
893
- throw new Error(`node ${nodeId} already has a migrated deadline (${String(rival['cron_id'])}); only one is allowed`);
894
- }
895
- }
896
- insert.run(triggerId, name, ownerId, command, fireAt, recur, expiresAt, nodeId, actionMode === 'deadline_message' ? 1 : 0, cwd, profile, 300,
897
- // `tier` and `sink` are INERT for migrated rows: the delivery lives entirely
898
- // inside `command` (which carries its own `--tier`), and `sink = '{}'`
899
- // parses to "no sink armed". `tier` is preserved only as provenance of what
900
- // the retired schedule would have sent.
901
- tier, created, created);
902
- }
903
- /** v23 — pid-REUSE guard for the cron run lease: `crons.run_pid_identity` holds
904
- * the `capturePidIdentities` fingerprint of the run's process, captured at lease
905
- * acquisition beside `run_pid`. Every kill site (stale-lease recovery,
906
- * `cancelCron`, `cancelCronsOnWake`, deadline displacement) re-captures the
907
- * identity of the recorded pid and refuses to signal unless it MATCHES.
908
- *
909
- * Without it, a bare pid recorded by a daemon life that ended (SIGKILL, host
910
- * reboot) is compared only with `isPidAlive` — after a reboot the pid comes
911
- * from a dead kernel's pid space, a low pid is likely recycled, and the run's
912
- * own timeout is trivially exceeded, so recovery SIGTERMs an unrelated user
913
- * process group. Rows written before this column exist have NULL identity and
914
- * therefore fall to the fail-closed path (release the lease, never signal). */
915
- function addCronRunPidIdentityColumn(db) {
916
- const columns = tableColumns(db, 'crons');
917
- // A metadata-only harness db may have no `crons` table at all (PRAGMA returns
918
- // no rows); there is nothing to alter and the version must still advance.
919
- if (columns.size === 0 || columns.has('run_pid_identity'))
920
- return;
921
- db.exec('ALTER TABLE crons ADD COLUMN run_pid_identity TEXT;');
922
- }
923
- /** v24 — mark an OUT-OF-BAND run lease, and drop the never-implemented
924
- * `crons.queued` column.
925
- *
926
- * `run_out_of_band` is set by `acquireCronRunLease` when the run is a `cron run`
927
- * (the manual verify verb) rather than a scheduled fire. The overlap pass
928
- * selects on `run_state = 'running'` alone, so without this marker a manual run
929
- * that happens to straddle a real occurrence gets that occurrence advanced past
930
- * (`overlap=skip` — a scheduled fire silently lost to a verification) or gets
931
- * itself SIGTERMed (`overlap=replace`). The overlap pass now excludes it.
932
- *
933
- * `queued` was written by nothing and read by nothing: `overlap='queue'` is
934
- * implemented purely by LEAVING `fire_at` past-due, so the depth is structural
935
- * (one occurrence per row) and needs no counter. A column documenting a policy
936
- * it does not implement misleads the next reader, so it goes. */
937
- function addCronOutOfBandColumn(db) {
938
- const columns = tableColumns(db, 'crons');
939
- // A metadata-only harness db may have no `crons` table at all (PRAGMA returns
940
- // no rows); there is nothing to alter and the version must still advance.
941
- if (columns.size === 0)
942
- return;
943
- if (!columns.has('run_out_of_band')) {
944
- db.exec('ALTER TABLE crons ADD COLUMN run_out_of_band INTEGER NOT NULL DEFAULT 0;');
945
- }
946
- if (columns.has('queued'))
947
- db.exec('ALTER TABLE crons DROP COLUMN queued;');
948
- }
949
- /** v25 — the `warm_pool` table: the spare-node pool behind `prefer_warm`.
950
- *
951
- * A spare IS a real canvas node (its broker is already booted against a real
952
- * node dir); the row here is the marker that it has not been handed to anyone
953
- * yet. Membership in this table is what hides a node from every listing
954
- * (`listNodes`/`rosterNodes`/`listResumableRoots`) — an unclaimed spare must
955
- * never surface as a phantom empty conversation in a user's sidebar. Claiming
956
- * is exactly the DELETE of this row, taken under the canvas write-lock, so two
957
- * concurrent creates can never be handed the same spare.
958
- *
959
- * `recipe_key` is the frozen-tuple digest a claim must match exactly (see
960
- * `runtime/warm-pool.ts`); the FK cascade reaps the marker when the node row
961
- * goes away. */
962
- function addWarmPoolTable(db) {
963
- db.exec(`
231
+ `)}i(Fe,"migrateTriggersToCrons");function ye(e,n,t,o,s){const T=L(t,"owner_id",o),r=e.prepare("SELECT cwd, profile_id FROM nodes WHERE node_id = ?").get(T),E=(r===void 0?void 0:R(r,"cwd"))??s,d=r===void 0?null:R(r,"profile_id")??null,_=R(t,"node_id")??null,c=L(t,"action",o),N=L(t,"action_mode",o),u=L(t,"trigger_type",o),m=De(t.payload),M=R(t,"created")??new Date().toISOString(),C=N==="deadline_message"?"urgent":U(m,"tier")??"normal",x=U(m,"label");let p,D,G=!1;if(c==="msg"&&(N==="inbox_message"||N==="deadline_message")){if(_===null)throw new Error("has no message target");const O=U(m,"body");O!==void 0?p=K(_,C,O,o):u==="when"?(G=!0,p=he(_,C)):p=K(_,C,x??"Scheduled message (no body was recorded when this schedule was armed).",o),D=x??(N==="deadline_message"?"deadline":"scheduled message")}else if(c==="msg"&&N==="fresh_revive"){if(_===null)throw new Error("has no revive target");p=`crtr node lifecycle revive ${f(_)} --fresh`,D=x??"scheduled fresh revive"}else if(c==="new"&&N==="node_birth")p=we(m,o),D=U(m,"name")??`scheduled ${L(m,"kind",o)} node`;else throw new Error(`has unsupported action ${c}/${N}`);let v,F,B=null;if(u==="when"){v=L(t,"next_eval_at",o),F=L(t,"eval_every",o),B=R(t,"timeout_at")??null;const O=L(t,"when_script",o);p=`${G?`if ! CRTR_GATE_STDOUT="$(
232
+ ${O}
233
+ )"; then`:`if ! (
234
+ ${O}
235
+ ); then`}
236
+ exit 0
237
+ fi
238
+ {
239
+ ${p}
240
+ } && crtr cron cancel "$CRTR_CRON_ID"`}else if(u==="at"||u==="every"||u==="until")v=L(t,"fire_at",o),F=u==="every"?L(t,"recur",o):null;else throw new Error(`has unknown timing type ${u}`);if(N==="deadline_message"&&_!==null){const O=e.prepare("SELECT cron_id FROM crons WHERE anchor_node = ? AND cancel_on_wake = 1 AND cron_id <> ?").get(_,o);if(O!==void 0)throw new Error(`node ${_} already has a migrated deadline (${String(O.cron_id)}); only one is allowed`)}n.run(o,D,T,p,v,F,B,_,N==="deadline_message"?1:0,E,d,300,C,M,M)}i(ye,"convertTriggerRow");function ke(e){const n=w(e,"crons");n.size===0||n.has("run_pid_identity")||e.exec("ALTER TABLE crons ADD COLUMN run_pid_identity TEXT;")}i(ke,"addCronRunPidIdentityColumn");function Me(e){const n=w(e,"crons");n.size!==0&&(n.has("run_out_of_band")||e.exec("ALTER TABLE crons ADD COLUMN run_out_of_band INTEGER NOT NULL DEFAULT 0;"),n.has("queued")&&e.exec("ALTER TABLE crons DROP COLUMN queued;"))}i(Me,"addCronOutOfBandColumn");function Ge(e){e.exec(`
964
241
  CREATE TABLE IF NOT EXISTS warm_pool (
965
242
  node_id TEXT PRIMARY KEY REFERENCES nodes(node_id) ON DELETE CASCADE,
966
243
  recipe_key TEXT NOT NULL, -- frozen launch tuple this spare was minted for
967
244
  created TEXT NOT NULL -- ISO 8601, mint time (oldest spare claimed first)
968
245
  );
969
246
  CREATE INDEX IF NOT EXISTS idx_warm_pool_recipe ON warm_pool(recipe_key, created);
970
- `);
971
- }
972
- /** v26 — narrow `consult_outbox` for the humanloop absorption into
973
- * `src/core/human/` (absorb-humanloop
974
- * design, "The human-work receipt table"; Landing 2 Part E task E2). The
975
- * five-column trust binding (`handler_command`, `handler_args_json`,
976
- * `claim_token`, `generation_id`, `interaction_snapshot`) existed only to let
977
- * crtrd re-verify that a Visual event arrived through crouter's own
978
- * registered handler argv — that registry is deleted in this landing, so
979
- * there is nothing left to bind. `dir`/`root` collapse into `ticket_node_id`,
980
- * the bridge node id stored as `basename(dir)` in the input rows.
981
- *
982
- * THIS IS A TABLE REBUILD, NOT `ALTER TABLE … DROP COLUMN`: six of the nine
983
- * existing indexes are on `dir` (`idx_consult_outbox_dir`,
984
- * `idx_consult_outbox_dir_request_status`, `idx_consult_outbox_dir_status`
985
- * from v18; `idx_consult_outbox_human_work_dir_status`,
986
- * `idx_consult_outbox_human_work_request_status`, and the partial-unique
987
- * `idx_consult_outbox_visual_request` from v19), and SQLite refuses
988
- * `DROP COLUMN` on any indexed column. `ticket_node_id` cannot be a SQL
989
- * DEFAULT either — SQLite has no `basename()` — so it is computed per row in
990
- * JS: read every existing row through a prepared SELECT, insert each into a
991
- * freshly created `consult_outbox_new` with `ticket_node_id = basename(dir)`,
992
- * drop the old table (dropping its indexes with it), rename the new table
993
- * into place, and recreate exactly five indexes on the narrowed shape. Every
994
- * row is carried, including terminal ones, EXCEPT a row whose legacy `dir` is
995
- * not a canonical direct child of its recorded `root`, or whose basename is
996
- * not a safe node id — either would create an unaddressable or aliased ticket
997
- * id once `root` is discarded. A warning names how many are dropped.
998
- *
999
- * THERE IS NO ROLLBACK. A sealed older runtime generation still running
1000
- * against this canvas.db fails on the Visual lane (`INSERT INTO
1001
- * consult_outbox (… dir, root, handler_command …)`) once this has run —
1002
- * acceptable because this migration lands WITH a generation roll
1003
- * (`npm run build && npm run install-runtime && crtr sys daemon restart`),
1004
- * never alongside one. Not self-transactional: like every ordinary migration
1005
- * it runs inside `migrate()`'s per-step `BEGIN IMMEDIATE`, so an interrupted
1006
- * run leaves `consult_outbox` exactly as it was (SQLite DDL is transactional)
1007
- * and a re-open resumes cleanly at the same step. */
1008
- function narrowHumanWorkOutbox(db) {
1009
- const rows = db
1010
- .prepare('SELECT node_id, dir, root, request_id, work_kind, status, final_report, updated_at FROM consult_outbox')
1011
- .all();
1012
- db.exec(`
247
+ `)}i(Ge,"addWarmPoolTable");function Be(e){const n=e.prepare("SELECT node_id, dir, root, request_id, work_kind, status, final_report, updated_at FROM consult_outbox").all();e.exec(`
1013
248
  CREATE TABLE consult_outbox_new (
1014
249
  node_id TEXT PRIMARY KEY,
1015
250
  ticket_node_id TEXT NOT NULL,
@@ -1019,24 +254,9 @@ CREATE TABLE consult_outbox_new (
1019
254
  final_report TEXT,
1020
255
  updated_at TEXT NOT NULL
1021
256
  );
1022
- `);
1023
- const insert = db.prepare(`
257
+ `);const t=e.prepare(`
1024
258
  INSERT INTO consult_outbox_new (node_id, ticket_node_id, request_id, work_kind, status, final_report, updated_at)
1025
- VALUES (?, ?, ?, ?, ?, ?, ?)`);
1026
- let dropped = 0;
1027
- for (const row of rows) {
1028
- const ticketNodeId = basename(row.dir);
1029
- const directChild = row.root === resolve(row.root) && row.dir === join(row.root, ticketNodeId);
1030
- if (!directChild || !isSafeNodeId(ticketNodeId)) {
1031
- dropped += 1;
1032
- continue;
1033
- }
1034
- insert.run(row.node_id, ticketNodeId, row.request_id, row.work_kind, row.status, row.final_report, row.updated_at);
1035
- }
1036
- if (dropped > 0) {
1037
- console.warn(`[canvas migration v26] dropped ${dropped} consult_outbox row(s) whose legacy ticket path cannot safely map to a ticket node id`);
1038
- }
1039
- db.exec(`
259
+ VALUES (?, ?, ?, ?, ?, ?, ?)`);let o=0;for(const s of n){const T=te(s.dir);if(!(s.root===H(s.root)&&s.dir===y(s.root,T))||!ie(T)){o+=1;continue}t.run(s.node_id,T,s.request_id,s.work_kind,s.status,s.final_report,s.updated_at)}o>0&&console.warn(`[canvas migration v26] dropped ${o} consult_outbox row(s) whose legacy ticket path cannot safely map to a ticket node id`),e.exec(`
1040
260
  DROP TABLE consult_outbox;
1041
261
  ALTER TABLE consult_outbox_new RENAME TO consult_outbox;
1042
262
 
@@ -1045,11 +265,7 @@ CREATE INDEX IF NOT EXISTS idx_consult_outbox_human_work_status ON consult_outbo
1045
265
  CREATE INDEX IF NOT EXISTS idx_consult_outbox_ticket_status ON consult_outbox(ticket_node_id, work_kind, status);
1046
266
  CREATE INDEX IF NOT EXISTS idx_consult_outbox_ticket_request_status ON consult_outbox(ticket_node_id, request_id, work_kind, status);
1047
267
  CREATE UNIQUE INDEX IF NOT EXISTS idx_consult_outbox_visual_request ON consult_outbox(ticket_node_id, request_id, work_kind) WHERE work_kind = 'visual';
1048
- `);
1049
- }
1050
- /** v27 — the canonical daemon-owned review record. */
1051
- function addReviewsTable(db) {
1052
- db.exec(`
268
+ `)}i(Be,"narrowHumanWorkOutbox");function He(e){e.exec(`
1053
269
  CREATE TABLE IF NOT EXISTS reviews (
1054
270
  review_id TEXT PRIMARY KEY,
1055
271
  idempotency_key TEXT NOT NULL UNIQUE,
@@ -1093,11 +309,7 @@ CREATE INDEX IF NOT EXISTS idx_reviews_state ON reviews(state);
1093
309
  CREATE INDEX IF NOT EXISTS idx_reviews_origin ON reviews(origin_node_id);
1094
310
  CREATE INDEX IF NOT EXISTS idx_reviews_file ON reviews(file);
1095
311
  CREATE INDEX IF NOT EXISTS idx_reviews_bridge ON reviews(bridge_node_id);
1096
- `);
1097
- }
1098
- /** v28 — current review-comment projection and append-only comment audit. */
1099
- function addReviewCommentTables(db) {
1100
- db.exec(`
312
+ `)}i(He,"addReviewsTable");function Pe(e){e.exec(`
1101
313
  CREATE TABLE IF NOT EXISTS review_comments (
1102
314
  comment_id TEXT PRIMARY KEY,
1103
315
  review_id TEXT NOT NULL,
@@ -1142,43 +354,13 @@ CREATE INDEX IF NOT EXISTS idx_review_comment_events_review_seq
1142
354
  ON review_comment_events(review_id, seq);
1143
355
  CREATE INDEX IF NOT EXISTS idx_review_comment_events_comment_seq
1144
356
  ON review_comment_events(comment_id, seq);
1145
- `);
1146
- }
1147
- /** v29 — durable review-comment anchor disposition. v28 is already released, so this corrects both fresh and migrated databases without rewriting its historical schema. */
1148
- function addReviewCommentAnchorState(db) {
1149
- db.exec(`
357
+ `)}i(Pe,"addReviewCommentTables");function be(e){e.exec(`
1150
358
  ALTER TABLE review_comments
1151
359
  ADD COLUMN anchor_state TEXT NOT NULL DEFAULT 'live' CHECK (anchor_state IN ('live', 'detached'));
1152
- `);
1153
- }
1154
- /** v30 — remove the retired human-work receipt table after every runtime reader is gone. */
1155
- function dropConsultOutbox(db) {
1156
- db.exec('DROP TABLE IF EXISTS consult_outbox');
1157
- }
1158
- /** v31 — a human's submit intent recorded on a still-open review, so the
1159
- * approval can wait for the companion to stop working. Deliberately a column
1160
- * and not a new `state` value: through the wait the review IS open — comments
1161
- * still land, ranges still remap, and cancellation still applies. */
1162
- function addReviewSubmitRequested(db) {
1163
- db.exec('ALTER TABLE reviews ADD COLUMN submit_requested_at TEXT');
1164
- }
1165
- /** v32 — held crons (the exit-75 owed-gate disposition). `held` marks a row
1166
- * whose last scheduled run exited 75 ("owed but not currently eligible"):
1167
- * the occurrence was not spent and the row waits for an eligibility poke or
1168
- * its natural backstop slot. `last_poke_at` records the most recent
1169
- * `POST /v1/crons/poke` receipt on EVERY row, closing the race where a poke
1170
- * lands while a gate check is in flight (the settling run compares its start
1171
- * against it and re-dues instead of parking). Deliberately not part of the
1172
- * due query: a held row is non-due by `fire_at`, never by a new predicate. */
1173
- function addCronHeldColumns(db) {
1174
- db.exec(`
360
+ `)}i(be,"addReviewCommentAnchorState");function Ye(e){e.exec("DROP TABLE IF EXISTS consult_outbox")}i(Ye,"dropConsultOutbox");function $e(e){e.exec("ALTER TABLE reviews ADD COLUMN submit_requested_at TEXT")}i($e,"addReviewSubmitRequested");function We(e){e.exec(`
1175
361
  ALTER TABLE crons ADD COLUMN held INTEGER NOT NULL DEFAULT 0;
1176
362
  ALTER TABLE crons ADD COLUMN last_poke_at TEXT;
1177
- `);
1178
- }
1179
- /** v33 — durable, daemon-owned attempts to deliver settled human completions. */
1180
- function addHumanActionDeliveries(db) {
1181
- db.exec(`
363
+ `)}i(We,"addCronHeldColumns");function Ke(e){e.exec(`
1182
364
  CREATE TABLE human_action_deliveries (
1183
365
  request_id TEXT PRIMARY KEY,
1184
366
  state TEXT NOT NULL,
@@ -1196,128 +378,18 @@ CREATE TABLE human_action_deliveries (
1196
378
  updated_at INTEGER NOT NULL
1197
379
  );
1198
380
  CREATE INDEX idx_human_action_deliveries_due ON human_action_deliveries(state, next_attempt_at);
1199
- `);
1200
- }
1201
- /** v34 — index the exact Pi session file coordinate used to recover fork
1202
- * exposure provenance without hydrating every node meta. Meta remains authoritative;
1203
- * normal identity upserts keep this projection current after the one-time backfill. */
1204
- function addNodeSessionFileIndex(db) {
1205
- const columns = nodeColumns(db);
1206
- addNodeColumnIfMissing(db, columns, 'pi_session_file', 'ALTER TABLE nodes ADD COLUMN pi_session_file TEXT;');
1207
- for (const entry of readdirSync(nodesRoot(), { withFileTypes: true })) {
1208
- if (!entry.isDirectory())
1209
- continue;
1210
- try {
1211
- const meta = JSON.parse(readFileSync(nodeMetaPath(entry.name), 'utf8'));
1212
- if (typeof meta.pi_session_file === 'string') {
1213
- db.prepare('UPDATE nodes SET pi_session_file = ? WHERE node_id = ?').run(meta.pi_session_file, entry.name);
1214
- }
1215
- }
1216
- catch {
1217
- // Corrupt node metadata is ignored by the ordinary canvas rebuild too.
1218
- }
1219
- }
1220
- db.exec('CREATE INDEX IF NOT EXISTS idx_nodes_pi_session_file ON nodes(pi_session_file);');
1221
- }
1222
- /** Reproject the derived session-file index from authoritative node metadata.
1223
- * v36 may resolve duplicate authoritative claimants because it runs before the
1224
- * first UNIQUE index exists. v37 must retain every surviving meta claim: a
1225
- * conflict at that later boundary is irreconcilable and fails instead. */
1226
- function reconcileNodeSessionFileOwners(db, clearDuplicateMetaClaimants) {
1227
- const canonical = (sessionFile) => {
1228
- const absolute = resolve(sessionFile);
1229
- return existsSync(absolute) ? realpathSync(absolute) : absolute;
1230
- };
1231
- const setFile = db.prepare('UPDATE nodes SET pi_session_file = ? WHERE node_id = ?');
1232
- db.exec('DROP INDEX IF EXISTS idx_nodes_pi_session_file;');
1233
- const rows = db.prepare('SELECT node_id FROM nodes ORDER BY created ASC, node_id ASC').all();
1234
- for (const { node_id } of rows) {
1235
- const metaPath = nodeMetaPath(node_id);
1236
- // Missing or unreadable metadata has no authoritative coordinate. Avoid
1237
- // taking a file lock there: old rows can outlive a removed node directory.
1238
- if (readMetaObject(metaPath) === null) {
1239
- setFile.run(null, node_id);
1240
- continue;
1241
- }
1242
- const sessionFile = withMetaLock(metaPath, () => {
1243
- const meta = readMetaObject(metaPath);
1244
- if (meta === null)
1245
- throw new Error(`node ${node_id} session metadata changed during ownership migration`);
1246
- if (typeof meta['pi_session_file'] !== 'string')
1247
- return null;
1248
- const storedSessionFile = meta['pi_session_file'];
1249
- const normalizedSessionFile = canonical(storedSessionFile);
1250
- if (normalizedSessionFile !== storedSessionFile) {
1251
- meta['pi_session_file'] = normalizedSessionFile;
1252
- writeMetaObjectLocked(metaPath, meta);
1253
- }
1254
- return normalizedSessionFile;
1255
- });
1256
- // meta.json is authoritative: a crash after its write can leave this row
1257
- // claiming another node's old session coordinate.
1258
- setFile.run(sessionFile, node_id);
1259
- }
1260
- const duplicates = db.prepare(`
381
+ `)}i(Ke,"addHumanActionDeliveries");function qe(e){const n=l(e);a(e,n,"pi_session_file","ALTER TABLE nodes ADD COLUMN pi_session_file TEXT;");for(const t of X(S(),{withFileTypes:!0}))if(t.isDirectory())try{const o=JSON.parse(h(I(t.name),"utf8"));typeof o.pi_session_file=="string"&&e.prepare("UPDATE nodes SET pi_session_file = ? WHERE node_id = ?").run(o.pi_session_file,t.name)}catch{}e.exec("CREATE INDEX IF NOT EXISTS idx_nodes_pi_session_file ON nodes(pi_session_file);")}i(qe,"addNodeSessionFileIndex");function j(e,n){const t=i(E=>{const d=H(E);return A(d)?ne(d):d},"canonical"),o=e.prepare("UPDATE nodes SET pi_session_file = ? WHERE node_id = ?");e.exec("DROP INDEX IF EXISTS idx_nodes_pi_session_file;");const s=e.prepare("SELECT node_id FROM nodes ORDER BY created ASC, node_id ASC").all();for(const{node_id:E}of s){const d=I(E);if(P(d)===null){o.run(null,E);continue}const _=Te(d,()=>{const c=P(d);if(c===null)throw new Error(`node ${E} session metadata changed during ownership migration`);if(typeof c.pi_session_file!="string")return null;const N=c.pi_session_file,u=t(N);return u!==N&&(c.pi_session_file=u,Ee(d,c)),u});o.run(_,E)}const T=e.prepare(`
1261
382
  SELECT pi_session_file
1262
383
  FROM nodes
1263
384
  WHERE pi_session_file IS NOT NULL
1264
385
  GROUP BY pi_session_file
1265
386
  HAVING COUNT(*) > 1
1266
- `).all();
1267
- if (!clearDuplicateMetaClaimants && duplicates.length > 0) {
1268
- const coordinates = duplicates.map(({ pi_session_file }) => pi_session_file).join(', ');
1269
- throw new Error(`cannot restore unique Pi session ownership: authoritative metadata has concurrent claimants for ${coordinates}`);
1270
- }
1271
- const clearRow = db.prepare('UPDATE nodes SET pi_session_file = NULL WHERE node_id = ?');
1272
- for (const { pi_session_file } of duplicates) {
1273
- const owners = db.prepare(`
387
+ `).all();if(!n&&T.length>0){const E=T.map(({pi_session_file:d})=>d).join(", ");throw new Error(`cannot restore unique Pi session ownership: authoritative metadata has concurrent claimants for ${E}`)}const r=e.prepare("UPDATE nodes SET pi_session_file = NULL WHERE node_id = ?");for(const{pi_session_file:E}of T){const d=e.prepare(`
1274
388
  SELECT node_id
1275
389
  FROM nodes
1276
390
  WHERE pi_session_file = ?
1277
391
  ORDER BY created ASC, node_id ASC
1278
- `).all(pi_session_file);
1279
- for (const { node_id } of owners.slice(1)) {
1280
- // Clear both durable coordinates so a later reindex cannot restore the
1281
- // duplicate projection. The checked write fails rather than erasing a
1282
- // concurrent metadata change.
1283
- const cleared = updateJsonFileDurably(nodeMetaPath(node_id), (meta) => {
1284
- const currentSessionFile = meta['pi_session_file'];
1285
- if (typeof currentSessionFile !== 'string' || canonical(currentSessionFile) !== pi_session_file) {
1286
- throw new Error(`node ${node_id} session metadata changed during ownership migration`);
1287
- }
1288
- meta['pi_session_id'] = null;
1289
- meta['pi_session_file'] = null;
1290
- return true;
1291
- });
1292
- if (!cleared)
1293
- throw new Error(`node ${node_id} session metadata changed during ownership migration`);
1294
- clearRow.run(node_id);
1295
- }
1296
- }
1297
- db.exec('CREATE UNIQUE INDEX IF NOT EXISTS idx_nodes_pi_session_file ON nodes(pi_session_file);');
1298
- }
1299
- /** v36 — one Pi transcript may have exactly one node owner. This is the narrow
1300
- * corrective body for clients below v36; it reprojects metadata before choosing
1301
- * the earliest created duplicate claimant (node_id breaks equal timestamps). */
1302
- function makeNodeSessionFileUnique(db) {
1303
- reconcileNodeSessionFileOwners(db, true);
1304
- }
1305
- /** v37 — repair v0.3.250's already-applied v36 projection without inventing
1306
- * coordinates v36 already cleared. Surviving authoritative metadata wins over
1307
- * stale rows; concurrent surviving claims fail loudly rather than clearing one. */
1308
- function repairNodeSessionFileUniqueIndex(db) {
1309
- reconcileNodeSessionFileOwners(db, false);
1310
- }
1311
- /** v35 — durable node lifecycle execution state and terminal cause. */
1312
- function addNodeLifecycleColumns(db) {
1313
- const columns = nodeColumns(db);
1314
- addNodeColumnIfMissing(db, columns, 'frozen_at', 'ALTER TABLE nodes ADD COLUMN frozen_at TEXT;');
1315
- addNodeColumnIfMissing(db, columns, 'respawn_failures', 'ALTER TABLE nodes ADD COLUMN respawn_failures INTEGER NOT NULL DEFAULT 0;');
1316
- addNodeColumnIfMissing(db, columns, 'respawn_not_before', 'ALTER TABLE nodes ADD COLUMN respawn_not_before TEXT;');
1317
- addNodeColumnIfMissing(db, columns, 'launched_at', 'ALTER TABLE nodes ADD COLUMN launched_at TEXT;');
1318
- addNodeColumnIfMissing(db, columns, 'last_settled_at', 'ALTER TABLE nodes ADD COLUMN last_settled_at TEXT;');
1319
- addNodeColumnIfMissing(db, columns, 'terminal_reason', 'ALTER TABLE nodes ADD COLUMN terminal_reason TEXT;');
1320
- db.exec(`
392
+ `).all(E);for(const{node_id:_}of d.slice(1)){if(!b(I(_),N=>{const u=N.pi_session_file;if(typeof u!="string"||t(u)!==E)throw new Error(`node ${_} session metadata changed during ownership migration`);return N.pi_session_id=null,N.pi_session_file=null,!0}))throw new Error(`node ${_} session metadata changed during ownership migration`);r.run(_)}}e.exec("CREATE UNIQUE INDEX IF NOT EXISTS idx_nodes_pi_session_file ON nodes(pi_session_file);")}i(j,"reconcileNodeSessionFileOwners");function je(e){j(e,!0)}i(je,"makeNodeSessionFileUnique");function ze(e){j(e,!1)}i(ze,"repairNodeSessionFileUniqueIndex");function Je(e){const n=l(e);a(e,n,"frozen_at","ALTER TABLE nodes ADD COLUMN frozen_at TEXT;"),a(e,n,"respawn_failures","ALTER TABLE nodes ADD COLUMN respawn_failures INTEGER NOT NULL DEFAULT 0;"),a(e,n,"respawn_not_before","ALTER TABLE nodes ADD COLUMN respawn_not_before TEXT;"),a(e,n,"launched_at","ALTER TABLE nodes ADD COLUMN launched_at TEXT;"),a(e,n,"last_settled_at","ALTER TABLE nodes ADD COLUMN last_settled_at TEXT;"),a(e,n,"terminal_reason","ALTER TABLE nodes ADD COLUMN terminal_reason TEXT;"),e.exec(`
1321
393
  UPDATE nodes SET terminal_reason = CASE
1322
394
  WHEN status = 'done' AND final_report IS NOT NULL THEN 'finalized'
1323
395
  WHEN status = 'done' AND intent = 'parked' THEN 'parked'
@@ -1326,51 +398,7 @@ UPDATE nodes SET terminal_reason = CASE
1326
398
  WHEN status = 'dead' THEN 'crashed'
1327
399
  END
1328
400
  WHERE status IN ('done','canceled','dead') AND terminal_reason IS NULL;
1329
- `);
1330
- }
1331
- /** v38 — mirror the two display-identity fields (`description`, `cycles`) that
1332
- * lived ONLY in meta.json onto the row, completing the identity projection the
1333
- * row index already is. Before this, every roster read that wanted a node's full
1334
- * label had to open and parse each node's meta.json (a per-node disk read on a
1335
- * path that already had all the other columns in one query). The backfill reads
1336
- * each meta once; from here `upsertRow`/`seedRow` maintain them like any other
1337
- * identity column, and `rebuildIndex` re-derives them. */
1338
- function addNodeLabelColumns(db) {
1339
- const columns = nodeColumns(db);
1340
- addNodeColumnIfMissing(db, columns, 'description', 'ALTER TABLE nodes ADD COLUMN description TEXT;');
1341
- addNodeColumnIfMissing(db, columns, 'cycles', 'ALTER TABLE nodes ADD COLUMN cycles INTEGER;');
1342
- const root = nodesRoot();
1343
- if (!existsSync(root))
1344
- return;
1345
- const upd = db.prepare('UPDATE nodes SET description = ?, cycles = ? WHERE node_id = ?');
1346
- for (const id of readdirSync(root)) {
1347
- const p = nodeMetaPath(id);
1348
- if (!existsSync(p))
1349
- continue;
1350
- let meta;
1351
- try {
1352
- meta = JSON.parse(readFileSync(p, 'utf8'));
1353
- }
1354
- catch {
1355
- continue; // a single unreadable meta never aborts the migration
1356
- }
1357
- const description = typeof meta['description'] === 'string' ? meta['description'] : null;
1358
- const cycles = typeof meta['cycles'] === 'number' ? meta['cycles'] : null;
1359
- upd.run(description, cycles, id);
1360
- }
1361
- }
1362
- /** v39 — durable terminal outcomes, spawn deadlines, and externally-owned
1363
- * outcome-delivery attempts. The outcome columns live on `nodes` so the same
1364
- * conditional terminal-status UPDATE can latch them atomically. */
1365
- function addNodeOutcomeAndDeadline(db) {
1366
- const columns = nodeColumns(db);
1367
- addNodeColumnIfMissing(db, columns, 'outcome_kind', 'ALTER TABLE nodes ADD COLUMN outcome_kind TEXT;');
1368
- addNodeColumnIfMissing(db, columns, 'outcome_reason', 'ALTER TABLE nodes ADD COLUMN outcome_reason TEXT;');
1369
- addNodeColumnIfMissing(db, columns, 'outcome_at', 'ALTER TABLE nodes ADD COLUMN outcome_at TEXT;');
1370
- addNodeColumnIfMissing(db, columns, 'outcome_revision', 'ALTER TABLE nodes ADD COLUMN outcome_revision INTEGER NOT NULL DEFAULT 0;');
1371
- addNodeColumnIfMissing(db, columns, 'outcome_detail_json', 'ALTER TABLE nodes ADD COLUMN outcome_detail_json TEXT;');
1372
- addNodeColumnIfMissing(db, columns, 'deadline_at', 'ALTER TABLE nodes ADD COLUMN deadline_at TEXT;');
1373
- db.exec(`
401
+ `)}i(Je,"addNodeLifecycleColumns");function Qe(e){const n=l(e);a(e,n,"description","ALTER TABLE nodes ADD COLUMN description TEXT;"),a(e,n,"cycles","ALTER TABLE nodes ADD COLUMN cycles INTEGER;");const t=S();if(!A(t))return;const o=e.prepare("UPDATE nodes SET description = ?, cycles = ? WHERE node_id = ?");for(const s of X(t)){const T=I(s);if(!A(T))continue;let r;try{r=JSON.parse(h(T,"utf8"))}catch{continue}const E=typeof r.description=="string"?r.description:null,d=typeof r.cycles=="number"?r.cycles:null;o.run(E,d,s)}}i(Qe,"addNodeLabelColumns");function Ve(e){const n=l(e);a(e,n,"outcome_kind","ALTER TABLE nodes ADD COLUMN outcome_kind TEXT;"),a(e,n,"outcome_reason","ALTER TABLE nodes ADD COLUMN outcome_reason TEXT;"),a(e,n,"outcome_at","ALTER TABLE nodes ADD COLUMN outcome_at TEXT;"),a(e,n,"outcome_revision","ALTER TABLE nodes ADD COLUMN outcome_revision INTEGER NOT NULL DEFAULT 0;"),a(e,n,"outcome_detail_json","ALTER TABLE nodes ADD COLUMN outcome_detail_json TEXT;"),a(e,n,"deadline_at","ALTER TABLE nodes ADD COLUMN deadline_at TEXT;"),e.exec(`
1374
402
  CREATE TABLE IF NOT EXISTS node_outcome_deliveries (
1375
403
  node_id TEXT PRIMARY KEY,
1376
404
  state TEXT NOT NULL,
@@ -1403,141 +431,4 @@ UPDATE nodes SET outcome_kind='failure',
1403
431
  outcome_reason=COALESCE(terminal_reason,'crashed'),
1404
432
  outcome_at=COALESCE(finalized_at, created), outcome_revision=1
1405
433
  WHERE final_report IS NULL AND status IN ('done','dead','canceled') AND outcome_at IS NULL;
1406
- `);
1407
- }
1408
- /** The journaled lane of the state-migration registry, adapted to this chain's
1409
- * step shape. Registry order is preserved, so these versions stay stable as
1410
- * long as the registry is append-only (same contract as the local list). */
1411
- const JOURNALED_STATE_MIGRATIONS = STATE_MIGRATIONS
1412
- .filter((m) => m.lane === 'journaled')
1413
- .map((m) => (db) => m.apply(db, crtrHome()));
1414
- /** The ordered migration list. Index `i` is migration version `i + 1`; the db's
1415
- * `user_version` tracks how many have been applied. Append only. Journaled
1416
- * entries from `src/migrations/registry.ts` follow the local steps, so a new
1417
- * registry migration lands as the next version. */
1418
- export const MIGRATIONS = [
1419
- /* v1 */ baselineSchema,
1420
- /* v2 */ addRuntimeColumns,
1421
- /* v3 */ backfillRuntime,
1422
- /* v4 */ edgesForeignKeyCascade,
1423
- /* v5 */ addPaneColumn,
1424
- /* v6 */ addFocusesTable,
1425
- /* v7 */ appendWakeupsTable,
1426
- /* v8 */ addHostKindColumn,
1427
- /* v9 */ migrateWakeupsToTriggers,
1428
- /* v10 */ addCanvasMetaTable,
1429
- /* v11 */ addProfileIdColumn,
1430
- /* v12 */ addPidIdentityColumn,
1431
- /* v13 */ addMessageWaitColumn,
1432
- /* v14 */ addCanonicalFinalColumns,
1433
- /* v15 */ normalizePersistedLaunchExtensions,
1434
- // Repair databases that reached v15 through the concurrent launch-metadata
1435
- // migration before canonical finalization joined the ordered mainline.
1436
- /* v16 */ addCanonicalFinalColumns,
1437
- /* v17 */ addMessageWaitGenerationColumn,
1438
- /* v18 */ addHumanWorkOutboxTable,
1439
- /* v19 */ addHumanWorkColumns,
1440
- /* v20 */ addNodeParentCreatedIndexes,
1441
- /* v21 */ addCronsTables,
1442
- /* v22 */ migrateTriggersToCrons,
1443
- /* v23 */ addCronRunPidIdentityColumn,
1444
- /* v24 */ addCronOutOfBandColumn,
1445
- /* v25 */ addWarmPoolTable,
1446
- /* v26 */ narrowHumanWorkOutbox,
1447
- /* v27 */ addReviewsTable,
1448
- /* v28 */ addReviewCommentTables,
1449
- /* v29 */ addReviewCommentAnchorState,
1450
- /* v30 */ dropConsultOutbox,
1451
- /* v31 */ addReviewSubmitRequested,
1452
- /* v32 */ addCronHeldColumns,
1453
- /* v33 */ addHumanActionDeliveries,
1454
- /* v34 */ addNodeSessionFileIndex,
1455
- /* v35 */ addNodeLifecycleColumns,
1456
- /* v36 */ makeNodeSessionFileUnique,
1457
- /* v37 */ repairNodeSessionFileUniqueIndex,
1458
- /* v38 */ addNodeLabelColumns,
1459
- /* v39 */ addNodeOutcomeAndDeadline,
1460
- ...JOURNALED_STATE_MIGRATIONS,
1461
- (db) => {
1462
- importNodeSqlAuthority(db);
1463
- migrateRecoveryWitnesses(db);
1464
- migrateMessagingState(db);
1465
- migrateHumanRequestsState(db);
1466
- },
1467
- ];
1468
- /** Migration indexes that manage their OWN transaction and therefore must not
1469
- * be wrapped by `migrate()` — `node:sqlite` rejects a nested BEGIN. Index 3
1470
- * (v4, the edges FK rebuild) both BEGINs internally and toggles
1471
- * `PRAGMA foreign_keys`, which is a no-op inside a transaction. Its docblock
1472
- * documents its own crash-safety: a partial rebuild rolls back and a re-run
1473
- * over an already-rebuilt table is idempotent. (Entering `migrate()` from
1474
- * INSIDE a caller's transaction with `user_version` still at 3 would make that
1475
- * internal BEGIN nest and throw; daemon startup calls it in autocommit.) */
1476
- const SELF_TRANSACTIONAL_MIGRATIONS = new Set([3]);
1477
- function currentUserVersion(db) {
1478
- return db.prepare('PRAGMA user_version').get().user_version;
1479
- }
1480
- function applyMigration(db, v) {
1481
- MIGRATIONS[v](db);
1482
- // `user_version` takes no bound parameters; v is a controlled integer.
1483
- db.exec(`PRAGMA user_version = ${v + 1}`);
1484
- }
1485
- /** Bring `db` up to the latest schema version. Reads `user_version`, runs each
1486
- * pending migration in order, and bumps `user_version` after each so the work
1487
- * is gated and idempotent: re-running is a no-op once `user_version` reaches
1488
- * `MIGRATIONS.length`. Forward-only.
1489
- *
1490
- * ATOMIC AND RESTARTABLE: each step AND its `user_version` bump run inside one
1491
- * `BEGIN IMMEDIATE`/`COMMIT` (SQLite journals `user_version` with the
1492
- * transaction, so a rollback restores it too). An interrupted or failing step
1493
- * therefore leaves the db exactly at the previous version with none of its
1494
- * writes committed — a half-applied step can never wedge every later open. The
1495
- * write lock also serializes concurrent openers; the version is re-read after
1496
- * acquiring it so a step another process just applied is skipped rather than
1497
- * re-run. */
1498
- export function migrate(db) {
1499
- const version = currentUserVersion(db);
1500
- if (version > MIGRATIONS.length) {
1501
- throw new Error(`unsupported canvas schema version ${version} (latest supported ${MIGRATIONS.length})`);
1502
- }
1503
- if (version === MIGRATIONS.length)
1504
- return;
1505
- // Pending work: a step now holds the write lock for its whole duration, and
1506
- // the fs-heavy legacy steps (v3/v14/v15) can outlast the ordinary 5s busy
1507
- // timeout. Let concurrent openers WAIT for the migration rather than fail.
1508
- const priorTimeout = db.prepare('PRAGMA busy_timeout').get().timeout;
1509
- db.exec('PRAGMA busy_timeout = 60000;');
1510
- try {
1511
- runPendingMigrations(db);
1512
- }
1513
- finally {
1514
- db.exec(`PRAGMA busy_timeout = ${priorTimeout};`);
1515
- }
1516
- }
1517
- function runPendingMigrations(db) {
1518
- for (;;) {
1519
- const v = currentUserVersion(db);
1520
- if (v >= MIGRATIONS.length)
1521
- return;
1522
- // Already inside a caller's transaction (or a self-transactional step):
1523
- // run bare rather than nesting a BEGIN node:sqlite would reject.
1524
- if (db.isTransaction || SELF_TRANSACTIONAL_MIGRATIONS.has(v)) {
1525
- applyMigration(db, v);
1526
- continue;
1527
- }
1528
- db.exec('BEGIN IMMEDIATE');
1529
- try {
1530
- // Another process may have applied this step while we waited on the lock.
1531
- if (currentUserVersion(db) === v)
1532
- applyMigration(db, v);
1533
- db.exec('COMMIT');
1534
- }
1535
- catch (err) {
1536
- try {
1537
- db.exec('ROLLBACK');
1538
- }
1539
- catch { /* transaction was already closed */ }
1540
- throw err;
1541
- }
1542
- }
1543
- }
434
+ `)}i(Ve,"addNodeOutcomeAndDeadline");const Ze=re.filter(e=>e.lane==="journaled").map(e=>n=>e.apply(n,oe())),g=[ae,de,_e,ce,Ne,ue,le,pe,Le,Oe,Ae,fe,Re,$,me,$,Ie,Xe,Se,Ue,ge,Fe,ke,Me,Ge,Be,He,Pe,be,Ye,$e,We,Ke,qe,Je,je,ze,Qe,Ve,...Ze,e=>{Q(e),V(e),Z(e),ee(e)}],en=new Set([3]);function k(e){return e.prepare("PRAGMA user_version").get().user_version}i(k,"currentUserVersion");function z(e,n){g[n](e),e.exec(`PRAGMA user_version = ${n+1}`)}i(z,"applyMigration");function ln(e){const n=k(e);if(n>g.length)throw new Error(`unsupported canvas schema version ${n} (latest supported ${g.length})`);if(n===g.length)return;const t=e.prepare("PRAGMA busy_timeout").get().timeout;e.exec("PRAGMA busy_timeout = 60000;");try{nn(e)}finally{e.exec(`PRAGMA busy_timeout = ${t};`)}}i(ln,"migrate");function nn(e){for(;;){const n=k(e);if(n>=g.length)return;if(e.isTransaction||en.has(n)){z(e,n);continue}e.exec("BEGIN IMMEDIATE");try{k(e)===n&&z(e,n),e.exec("COMMIT")}catch(t){try{e.exec("ROLLBACK")}catch{}throw t}}}i(nn,"runPendingMigrations");export{g as MIGRATIONS,ln as migrate};