woozlit 2.3.0 → 2.3.1

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 (1118) hide show
  1. package/{src/skill/compose/LICENSE-superpowers → LICENSE} +21 -26
  2. package/package.json +18 -191
  3. package/AGENTS.md +0 -134
  4. package/Dockerfile +0 -18
  5. package/README.md +0 -15
  6. package/bunfig.toml +0 -7
  7. package/drizzle.config.ts +0 -10
  8. package/git +0 -0
  9. package/migration/20260127222353_familiar_lady_ursula/migration.sql +0 -90
  10. package/migration/20260127222353_familiar_lady_ursula/snapshot.json +0 -796
  11. package/migration/20260211171708_add_project_commands/migration.sql +0 -1
  12. package/migration/20260211171708_add_project_commands/snapshot.json +0 -806
  13. package/migration/20260213144116_wakeful_the_professor/migration.sql +0 -11
  14. package/migration/20260213144116_wakeful_the_professor/snapshot.json +0 -897
  15. package/migration/20260225215848_workspace/migration.sql +0 -7
  16. package/migration/20260225215848_workspace/snapshot.json +0 -959
  17. package/migration/20260227213759_add_session_workspace_id/migration.sql +0 -2
  18. package/migration/20260227213759_add_session_workspace_id/snapshot.json +0 -983
  19. package/migration/20260228203230_blue_harpoon/migration.sql +0 -17
  20. package/migration/20260228203230_blue_harpoon/snapshot.json +0 -1102
  21. package/migration/20260303231226_add_workspace_fields/migration.sql +0 -5
  22. package/migration/20260303231226_add_workspace_fields/snapshot.json +0 -1013
  23. package/migration/20260309230000_move_org_to_state/migration.sql +0 -3
  24. package/migration/20260309230000_move_org_to_state/snapshot.json +0 -1156
  25. package/migration/20260312043431_session_message_cursor/migration.sql +0 -4
  26. package/migration/20260312043431_session_message_cursor/snapshot.json +0 -1168
  27. package/migration/20260323234822_events/migration.sql +0 -13
  28. package/migration/20260323234822_events/snapshot.json +0 -1271
  29. package/migration/20260410174513_workspace-name/migration.sql +0 -16
  30. package/migration/20260410174513_workspace-name/snapshot.json +0 -1271
  31. package/migration/20260413175956_chief_energizer/migration.sql +0 -13
  32. package/migration/20260413175956_chief_energizer/snapshot.json +0 -1399
  33. package/migration/20260422160000_context_inheritance/migration.sql +0 -3
  34. package/migration/20260422170000_task_registry/migration.sql +0 -18
  35. package/migration/20260423145421_remove_session_entry/migration.sql +0 -4
  36. package/migration/20260515000000_actor_rename/migration.sql +0 -7
  37. package/migration/20260515010000_memory_fts/migration.sql +0 -33
  38. package/migration/20260515020000_user_task/migration.sql +0 -29
  39. package/migration/20260519000000_last_checkpoint_message_id/migration.sql +0 -1
  40. package/migration/20260521000000_message_agent_id/migration.sql +0 -2
  41. package/migration/20260521000100_actor_registry_v6/migration.sql +0 -25
  42. package/migration/20260521010000_memory_fts_v6/migration.sql +0 -33
  43. package/migration/20260521020000_memory_fts_triggers/migration.sql +0 -17
  44. package/migration/20260526000000_agent_id_main/migration.sql +0 -14
  45. package/migration/20260527000000_actor_lifecycle/migration.sql +0 -8
  46. package/migration/20260527000100_inbox/migration.sql +0 -12
  47. package/migration/20260529000000_task_todo_redesign/migration.sql +0 -16
  48. package/migration/20260603000000_task_in_progress_owner/migration.sql +0 -1
  49. package/migration/20260603000000_workflow_run/migration.sql +0 -17
  50. package/migration/20260604000000_workflow_script_sha/migration.sql +0 -1
  51. package/migration/20260608000000_claude_import/migration.sql +0 -7
  52. package/migration/20260608010000_claude_import_message_ids/migration.sql +0 -1
  53. package/migration/20260609000000_history_fts/migration.sql +0 -29
  54. package/migration/20260609230000_workflow_agent_timeout/migration.sql +0 -1
  55. package/parsers-config.ts +0 -290
  56. package/script/build.ts +0 -269
  57. package/script/check-migrations.ts +0 -16
  58. package/script/fix-node-pty.ts +0 -28
  59. package/script/generate.ts +0 -23
  60. package/script/publish.ts +0 -75
  61. package/script/run-workspace-server +0 -106
  62. package/script/schema.ts +0 -63
  63. package/script/time.ts +0 -6
  64. package/script/trace-imports.ts +0 -153
  65. package/script/upgrade-opentui.ts +0 -64
  66. package/src/account/account.sql.ts +0 -39
  67. package/src/account/account.ts +0 -456
  68. package/src/account/repo.ts +0 -166
  69. package/src/account/schema.ts +0 -99
  70. package/src/account/url.ts +0 -8
  71. package/src/acp/README.md +0 -174
  72. package/src/acp/agent.ts +0 -1783
  73. package/src/acp/session.ts +0 -116
  74. package/src/acp/types.ts +0 -24
  75. package/src/actor/actor.sql.ts +0 -38
  76. package/src/actor/events.ts +0 -67
  77. package/src/actor/index.ts +0 -2
  78. package/src/actor/registry.ts +0 -412
  79. package/src/actor/return-header.ts +0 -24
  80. package/src/actor/schema.ts +0 -47
  81. package/src/actor/spawn-ref.ts +0 -16
  82. package/src/actor/spawn.ts +0 -741
  83. package/src/actor/turn.ts +0 -49
  84. package/src/actor/waiter.ts +0 -166
  85. package/src/agent/agent.ts +0 -554
  86. package/src/agent/config.ts +0 -5
  87. package/src/agent/generate.txt +0 -75
  88. package/src/agent/prompt/checkpoint-writer.txt +0 -167
  89. package/src/agent/prompt/compaction.txt +0 -9
  90. package/src/agent/prompt/distill.txt +0 -199
  91. package/src/agent/prompt/dream.txt +0 -155
  92. package/src/agent/prompt/explore.txt +0 -18
  93. package/src/agent/prompt/summary.txt +0 -11
  94. package/src/agent/prompt/title.txt +0 -44
  95. package/src/audio.d.ts +0 -9
  96. package/src/auth/index.ts +0 -106
  97. package/src/bus/bus-event.ts +0 -33
  98. package/src/bus/global.ts +0 -12
  99. package/src/bus/index.ts +0 -193
  100. package/src/cli/bootstrap.ts +0 -33
  101. package/src/cli/cmd/account.ts +0 -258
  102. package/src/cli/cmd/acp.ts +0 -70
  103. package/src/cli/cmd/agent.ts +0 -248
  104. package/src/cli/cmd/cmd.ts +0 -7
  105. package/src/cli/cmd/db.ts +0 -120
  106. package/src/cli/cmd/debug/agent.ts +0 -192
  107. package/src/cli/cmd/debug/config.ts +0 -17
  108. package/src/cli/cmd/debug/file.ts +0 -100
  109. package/src/cli/cmd/debug/index.ts +0 -48
  110. package/src/cli/cmd/debug/lsp.ts +0 -61
  111. package/src/cli/cmd/debug/ripgrep.ts +0 -105
  112. package/src/cli/cmd/debug/scrap.ts +0 -16
  113. package/src/cli/cmd/debug/skill.ts +0 -23
  114. package/src/cli/cmd/debug/snapshot.ts +0 -53
  115. package/src/cli/cmd/export.ts +0 -306
  116. package/src/cli/cmd/generate.ts +0 -50
  117. package/src/cli/cmd/github.ts +0 -1647
  118. package/src/cli/cmd/import.ts +0 -208
  119. package/src/cli/cmd/mcp.ts +0 -812
  120. package/src/cli/cmd/models.ts +0 -88
  121. package/src/cli/cmd/plug.ts +0 -233
  122. package/src/cli/cmd/pr.ts +0 -138
  123. package/src/cli/cmd/providers.ts +0 -689
  124. package/src/cli/cmd/run-completion.ts +0 -77
  125. package/src/cli/cmd/run.ts +0 -694
  126. package/src/cli/cmd/serve.ts +0 -21
  127. package/src/cli/cmd/session.ts +0 -181
  128. package/src/cli/cmd/stats.ts +0 -413
  129. package/src/cli/cmd/tui/app.tsx +0 -1349
  130. package/src/cli/cmd/tui/asset/TEN_VAD_LICENSE +0 -12
  131. package/src/cli/cmd/tui/asset/charge.wav +0 -0
  132. package/src/cli/cmd/tui/asset/pulse-a.wav +0 -0
  133. package/src/cli/cmd/tui/asset/pulse-b.wav +0 -0
  134. package/src/cli/cmd/tui/asset/pulse-c.wav +0 -0
  135. package/src/cli/cmd/tui/asset/ten_vad.wasm +0 -0
  136. package/src/cli/cmd/tui/asset/ten_vad_loader.js +0 -30
  137. package/src/cli/cmd/tui/attach.ts +0 -83
  138. package/src/cli/cmd/tui/component/background-image.tsx +0 -150
  139. package/src/cli/cmd/tui/component/bg-pulse.tsx +0 -130
  140. package/src/cli/cmd/tui/component/border.tsx +0 -21
  141. package/src/cli/cmd/tui/component/dialog-agent.tsx +0 -31
  142. package/src/cli/cmd/tui/component/dialog-command.tsx +0 -208
  143. package/src/cli/cmd/tui/component/dialog-console-org.tsx +0 -103
  144. package/src/cli/cmd/tui/component/dialog-go-upsell.tsx +0 -157
  145. package/src/cli/cmd/tui/component/dialog-image-list.tsx +0 -111
  146. package/src/cli/cmd/tui/component/dialog-logo-design.tsx +0 -37
  147. package/src/cli/cmd/tui/component/dialog-mcp.tsx +0 -86
  148. package/src/cli/cmd/tui/component/dialog-model.tsx +0 -260
  149. package/src/cli/cmd/tui/component/dialog-provider.tsx +0 -454
  150. package/src/cli/cmd/tui/component/dialog-session-delete-failed.tsx +0 -101
  151. package/src/cli/cmd/tui/component/dialog-session-list.tsx +0 -269
  152. package/src/cli/cmd/tui/component/dialog-session-rename.tsx +0 -31
  153. package/src/cli/cmd/tui/component/dialog-skill.tsx +0 -42
  154. package/src/cli/cmd/tui/component/dialog-stash.tsx +0 -87
  155. package/src/cli/cmd/tui/component/dialog-status.tsx +0 -170
  156. package/src/cli/cmd/tui/component/dialog-tag.tsx +0 -44
  157. package/src/cli/cmd/tui/component/dialog-theme-list.tsx +0 -50
  158. package/src/cli/cmd/tui/component/dialog-variant.tsx +0 -39
  159. package/src/cli/cmd/tui/component/dialog-woozlit-login.tsx +0 -206
  160. package/src/cli/cmd/tui/component/dialog-workflows.tsx +0 -62
  161. package/src/cli/cmd/tui/component/dialog-workspace-create.tsx +0 -289
  162. package/src/cli/cmd/tui/component/dialog-workspace-unavailable.tsx +0 -81
  163. package/src/cli/cmd/tui/component/dialog-worktree.tsx +0 -90
  164. package/src/cli/cmd/tui/component/error-component.tsx +0 -92
  165. package/src/cli/cmd/tui/component/logo.tsx +0 -961
  166. package/src/cli/cmd/tui/component/plugin-route-missing.tsx +0 -14
  167. package/src/cli/cmd/tui/component/prompt/autocomplete.tsx +0 -684
  168. package/src/cli/cmd/tui/component/prompt/cwd.ts +0 -0
  169. package/src/cli/cmd/tui/component/prompt/frecency.tsx +0 -90
  170. package/src/cli/cmd/tui/component/prompt/history.tsx +0 -108
  171. package/src/cli/cmd/tui/component/prompt/index.tsx +0 -1829
  172. package/src/cli/cmd/tui/component/prompt/part.ts +0 -16
  173. package/src/cli/cmd/tui/component/prompt/stash.tsx +0 -101
  174. package/src/cli/cmd/tui/component/spinner.tsx +0 -24
  175. package/src/cli/cmd/tui/component/starry-background.tsx +0 -305
  176. package/src/cli/cmd/tui/component/startup-loading.tsx +0 -67
  177. package/src/cli/cmd/tui/component/task-item.tsx +0 -63
  178. package/src/cli/cmd/tui/component/textarea-keybindings.ts +0 -73
  179. package/src/cli/cmd/tui/component/todo-item.tsx +0 -32
  180. package/src/cli/cmd/tui/config/cwd.ts +0 -5
  181. package/src/cli/cmd/tui/config/tui-migrate.ts +0 -151
  182. package/src/cli/cmd/tui/config/tui-schema.ts +0 -38
  183. package/src/cli/cmd/tui/config/tui.ts +0 -219
  184. package/src/cli/cmd/tui/context/args.tsx +0 -16
  185. package/src/cli/cmd/tui/context/directory.ts +0 -15
  186. package/src/cli/cmd/tui/context/event.ts +0 -45
  187. package/src/cli/cmd/tui/context/exit.tsx +0 -65
  188. package/src/cli/cmd/tui/context/helper.tsx +0 -25
  189. package/src/cli/cmd/tui/context/keybind.tsx +0 -105
  190. package/src/cli/cmd/tui/context/kv.tsx +0 -76
  191. package/src/cli/cmd/tui/context/language.tsx +0 -91
  192. package/src/cli/cmd/tui/context/local.tsx +0 -455
  193. package/src/cli/cmd/tui/context/plugin-keybinds.ts +0 -41
  194. package/src/cli/cmd/tui/context/project.tsx +0 -109
  195. package/src/cli/cmd/tui/context/prompt.tsx +0 -18
  196. package/src/cli/cmd/tui/context/route.tsx +0 -61
  197. package/src/cli/cmd/tui/context/sdk.tsx +0 -150
  198. package/src/cli/cmd/tui/context/sync.tsx +0 -828
  199. package/src/cli/cmd/tui/context/theme/aura.json +0 -69
  200. package/src/cli/cmd/tui/context/theme/ayu.json +0 -80
  201. package/src/cli/cmd/tui/context/theme/carbonfox.json +0 -248
  202. package/src/cli/cmd/tui/context/theme/catppuccin-frappe.json +0 -230
  203. package/src/cli/cmd/tui/context/theme/catppuccin-macchiato.json +0 -230
  204. package/src/cli/cmd/tui/context/theme/catppuccin.json +0 -112
  205. package/src/cli/cmd/tui/context/theme/cobalt2.json +0 -225
  206. package/src/cli/cmd/tui/context/theme/cursor.json +0 -249
  207. package/src/cli/cmd/tui/context/theme/dracula.json +0 -219
  208. package/src/cli/cmd/tui/context/theme/everforest.json +0 -241
  209. package/src/cli/cmd/tui/context/theme/flexoki.json +0 -237
  210. package/src/cli/cmd/tui/context/theme/github.json +0 -233
  211. package/src/cli/cmd/tui/context/theme/gruvbox.json +0 -242
  212. package/src/cli/cmd/tui/context/theme/kanagawa.json +0 -77
  213. package/src/cli/cmd/tui/context/theme/lucent-orng.json +0 -232
  214. package/src/cli/cmd/tui/context/theme/material.json +0 -235
  215. package/src/cli/cmd/tui/context/theme/matrix.json +0 -77
  216. package/src/cli/cmd/tui/context/theme/mercury.json +0 -252
  217. package/src/cli/cmd/tui/context/theme/mimocode.json +0 -245
  218. package/src/cli/cmd/tui/context/theme/monokai.json +0 -221
  219. package/src/cli/cmd/tui/context/theme/nightowl.json +0 -221
  220. package/src/cli/cmd/tui/context/theme/nord.json +0 -223
  221. package/src/cli/cmd/tui/context/theme/one-dark.json +0 -84
  222. package/src/cli/cmd/tui/context/theme/orng.json +0 -247
  223. package/src/cli/cmd/tui/context/theme/osaka-jade.json +0 -93
  224. package/src/cli/cmd/tui/context/theme/palenight.json +0 -222
  225. package/src/cli/cmd/tui/context/theme/rosepine.json +0 -234
  226. package/src/cli/cmd/tui/context/theme/solarized.json +0 -223
  227. package/src/cli/cmd/tui/context/theme/synthwave84.json +0 -226
  228. package/src/cli/cmd/tui/context/theme/tokyonight.json +0 -243
  229. package/src/cli/cmd/tui/context/theme/vercel.json +0 -245
  230. package/src/cli/cmd/tui/context/theme/vesper.json +0 -218
  231. package/src/cli/cmd/tui/context/theme/woozlit.json +0 -245
  232. package/src/cli/cmd/tui/context/theme/zenburn.json +0 -223
  233. package/src/cli/cmd/tui/context/theme.tsx +0 -1298
  234. package/src/cli/cmd/tui/context/thinking.ts +0 -48
  235. package/src/cli/cmd/tui/context/tui-config.tsx +0 -9
  236. package/src/cli/cmd/tui/event.ts +0 -56
  237. package/src/cli/cmd/tui/feature-plugins/home/footer.tsx +0 -93
  238. package/src/cli/cmd/tui/feature-plugins/home/tips-view.tsx +0 -193
  239. package/src/cli/cmd/tui/feature-plugins/home/tips.tsx +0 -54
  240. package/src/cli/cmd/tui/feature-plugins/sidebar/context.tsx +0 -169
  241. package/src/cli/cmd/tui/feature-plugins/sidebar/cwd.tsx +0 -45
  242. package/src/cli/cmd/tui/feature-plugins/sidebar/files.tsx +0 -62
  243. package/src/cli/cmd/tui/feature-plugins/sidebar/footer.tsx +0 -93
  244. package/src/cli/cmd/tui/feature-plugins/sidebar/goal.tsx +0 -84
  245. package/src/cli/cmd/tui/feature-plugins/sidebar/instructions.tsx +0 -54
  246. package/src/cli/cmd/tui/feature-plugins/sidebar/lsp.tsx +0 -66
  247. package/src/cli/cmd/tui/feature-plugins/sidebar/mcp.tsx +0 -98
  248. package/src/cli/cmd/tui/feature-plugins/sidebar/task.tsx +0 -95
  249. package/src/cli/cmd/tui/feature-plugins/sidebar/todo.tsx +0 -51
  250. package/src/cli/cmd/tui/feature-plugins/sidebar/tps.ts +0 -31
  251. package/src/cli/cmd/tui/feature-plugins/system/plugins.tsx +0 -274
  252. package/src/cli/cmd/tui/i18n/en.ts +0 -397
  253. package/src/cli/cmd/tui/i18n/es.ts +0 -433
  254. package/src/cli/cmd/tui/i18n/fr.ts +0 -440
  255. package/src/cli/cmd/tui/i18n/ja.ts +0 -392
  256. package/src/cli/cmd/tui/i18n/locales.ts +0 -82
  257. package/src/cli/cmd/tui/i18n/ru.ts +0 -452
  258. package/src/cli/cmd/tui/i18n/zh.ts +0 -390
  259. package/src/cli/cmd/tui/i18n/zht.ts +0 -360
  260. package/src/cli/cmd/tui/layer.ts +0 -6
  261. package/src/cli/cmd/tui/plugin/api.tsx +0 -405
  262. package/src/cli/cmd/tui/plugin/index.ts +0 -3
  263. package/src/cli/cmd/tui/plugin/internal.ts +0 -35
  264. package/src/cli/cmd/tui/plugin/runtime.ts +0 -1030
  265. package/src/cli/cmd/tui/plugin/slots.tsx +0 -60
  266. package/src/cli/cmd/tui/routes/home.tsx +0 -172
  267. package/src/cli/cmd/tui/routes/session/dialog-fork-from-timeline.tsx +0 -76
  268. package/src/cli/cmd/tui/routes/session/dialog-message.tsx +0 -116
  269. package/src/cli/cmd/tui/routes/session/dialog-subagent.tsx +0 -47
  270. package/src/cli/cmd/tui/routes/session/dialog-timeline.tsx +0 -47
  271. package/src/cli/cmd/tui/routes/session/footer.tsx +0 -91
  272. package/src/cli/cmd/tui/routes/session/index.tsx +0 -2532
  273. package/src/cli/cmd/tui/routes/session/permission.tsx +0 -691
  274. package/src/cli/cmd/tui/routes/session/question.tsx +0 -488
  275. package/src/cli/cmd/tui/routes/session/sidebar.tsx +0 -97
  276. package/src/cli/cmd/tui/routes/session/subagent-footer.tsx +0 -142
  277. package/src/cli/cmd/tui/thread.ts +0 -246
  278. package/src/cli/cmd/tui/ui/dialog-alert.tsx +0 -61
  279. package/src/cli/cmd/tui/ui/dialog-confirm.tsx +0 -95
  280. package/src/cli/cmd/tui/ui/dialog-export-options.tsx +0 -223
  281. package/src/cli/cmd/tui/ui/dialog-help.tsx +0 -42
  282. package/src/cli/cmd/tui/ui/dialog-prompt.tsx +0 -123
  283. package/src/cli/cmd/tui/ui/dialog-select.tsx +0 -452
  284. package/src/cli/cmd/tui/ui/dialog.tsx +0 -207
  285. package/src/cli/cmd/tui/ui/link.tsx +0 -28
  286. package/src/cli/cmd/tui/ui/spinner.ts +0 -378
  287. package/src/cli/cmd/tui/ui/toast.tsx +0 -102
  288. package/src/cli/cmd/tui/util/clipboard.ts +0 -203
  289. package/src/cli/cmd/tui/util/editor.ts +0 -35
  290. package/src/cli/cmd/tui/util/image-protocol.ts +0 -35
  291. package/src/cli/cmd/tui/util/index.ts +0 -6
  292. package/src/cli/cmd/tui/util/model.ts +0 -23
  293. package/src/cli/cmd/tui/util/provider-origin.ts +0 -7
  294. package/src/cli/cmd/tui/util/revert-diff.ts +0 -18
  295. package/src/cli/cmd/tui/util/scroll.ts +0 -23
  296. package/src/cli/cmd/tui/util/selection.ts +0 -23
  297. package/src/cli/cmd/tui/util/signal.ts +0 -41
  298. package/src/cli/cmd/tui/util/sound.ts +0 -154
  299. package/src/cli/cmd/tui/util/system-locale.ts +0 -209
  300. package/src/cli/cmd/tui/util/terminal.ts +0 -110
  301. package/src/cli/cmd/tui/util/transcript.ts +0 -112
  302. package/src/cli/cmd/tui/util/vad.ts +0 -229
  303. package/src/cli/cmd/tui/util/voice.ts +0 -360
  304. package/src/cli/cmd/tui/win32.ts +0 -130
  305. package/src/cli/cmd/tui/worker.ts +0 -104
  306. package/src/cli/cmd/uninstall.ts +0 -351
  307. package/src/cli/cmd/upgrade.ts +0 -79
  308. package/src/cli/cmd/web.ts +0 -81
  309. package/src/cli/effect/prompt.ts +0 -25
  310. package/src/cli/error.ts +0 -82
  311. package/src/cli/heap.ts +0 -59
  312. package/src/cli/i18n.ts +0 -15
  313. package/src/cli/logo.ts +0 -59
  314. package/src/cli/network.ts +0 -62
  315. package/src/cli/ui.ts +0 -133
  316. package/src/cli/upgrade.ts +0 -41
  317. package/src/command/index.ts +0 -276
  318. package/src/command/template/initialize.txt +0 -66
  319. package/src/command/template/review.txt +0 -101
  320. package/src/config/agent.ts +0 -197
  321. package/src/config/command.ts +0 -69
  322. package/src/config/config.ts +0 -1024
  323. package/src/config/console-state.ts +0 -16
  324. package/src/config/entry-name.ts +0 -16
  325. package/src/config/error.ts +0 -21
  326. package/src/config/formatter.ts +0 -17
  327. package/src/config/history.ts +0 -21
  328. package/src/config/index.ts +0 -16
  329. package/src/config/keybinds.ts +0 -127
  330. package/src/config/layout.ts +0 -10
  331. package/src/config/lsp.ts +0 -45
  332. package/src/config/managed.ts +0 -70
  333. package/src/config/markdown.ts +0 -97
  334. package/src/config/mcp.ts +0 -172
  335. package/src/config/model-id.ts +0 -14
  336. package/src/config/parse.ts +0 -44
  337. package/src/config/paths.ts +0 -73
  338. package/src/config/permission.ts +0 -76
  339. package/src/config/plugin.ts +0 -88
  340. package/src/config/provider.ts +0 -118
  341. package/src/config/server.ts +0 -20
  342. package/src/config/skills.ts +0 -16
  343. package/src/config/variable.ts +0 -90
  344. package/src/control-plane/adaptors/index.ts +0 -52
  345. package/src/control-plane/adaptors/worktree.ts +0 -47
  346. package/src/control-plane/dev/debug-workspace-plugin.ts +0 -73
  347. package/src/control-plane/schema.ts +0 -19
  348. package/src/control-plane/sse.ts +0 -66
  349. package/src/control-plane/types.ts +0 -34
  350. package/src/control-plane/util.ts +0 -37
  351. package/src/control-plane/workspace-context.ts +0 -26
  352. package/src/control-plane/workspace.sql.ts +0 -17
  353. package/src/control-plane/workspace.ts +0 -615
  354. package/src/effect/app-runtime.ts +0 -146
  355. package/src/effect/bootstrap-runtime.ts +0 -33
  356. package/src/effect/bridge.ts +0 -48
  357. package/src/effect/cross-spawn-spawner.ts +0 -514
  358. package/src/effect/index.ts +0 -5
  359. package/src/effect/instance-ref.ts +0 -11
  360. package/src/effect/instance-registry.ts +0 -12
  361. package/src/effect/instance-state.ts +0 -81
  362. package/src/effect/logger.ts +0 -73
  363. package/src/effect/memo-map.ts +0 -3
  364. package/src/effect/observability.ts +0 -107
  365. package/src/effect/run-service.ts +0 -52
  366. package/src/effect/runner.ts +0 -210
  367. package/src/effect/runtime.ts +0 -19
  368. package/src/env/index.ts +0 -37
  369. package/src/file/ignore.ts +0 -81
  370. package/src/file/index.ts +0 -664
  371. package/src/file/protected.ts +0 -59
  372. package/src/file/ripgrep.ts +0 -485
  373. package/src/file/watcher.ts +0 -163
  374. package/src/flag/flag.ts +0 -172
  375. package/src/format/formatter.ts +0 -403
  376. package/src/format/index.ts +0 -203
  377. package/src/git/index.ts +0 -260
  378. package/src/global/index.ts +0 -54
  379. package/src/history/backfill.ts +0 -162
  380. package/src/history/extract.ts +0 -67
  381. package/src/history/fts-query.ts +0 -15
  382. package/src/history/fts.sql.ts +0 -20
  383. package/src/history/index.ts +0 -10
  384. package/src/history/resolve.ts +0 -65
  385. package/src/history/service.ts +0 -258
  386. package/src/history/writer.ts +0 -112
  387. package/src/id/id.ts +0 -87
  388. package/src/ide/index.ts +0 -73
  389. package/src/inbox/inbox-ref.ts +0 -38
  390. package/src/inbox/inbox.sql.ts +0 -26
  391. package/src/inbox/inbox.ts +0 -223
  392. package/src/inbox/index.ts +0 -3
  393. package/src/inbox/render.ts +0 -40
  394. package/src/index.ts +0 -260
  395. package/src/installation/index.ts +0 -351
  396. package/src/installation/version.ts +0 -8
  397. package/src/lsp/client.ts +0 -249
  398. package/src/lsp/diagnostic.ts +0 -29
  399. package/src/lsp/index.ts +0 -3
  400. package/src/lsp/language.ts +0 -120
  401. package/src/lsp/launch.ts +0 -21
  402. package/src/lsp/lsp.ts +0 -519
  403. package/src/lsp/server.ts +0 -1956
  404. package/src/mcp/auth.ts +0 -144
  405. package/src/mcp/index.ts +0 -944
  406. package/src/mcp/oauth-callback.ts +0 -232
  407. package/src/mcp/oauth-provider.ts +0 -214
  408. package/src/memory/fts-query.ts +0 -37
  409. package/src/memory/fts.sql.ts +0 -19
  410. package/src/memory/index.ts +0 -1
  411. package/src/memory/paths.ts +0 -116
  412. package/src/memory/reconcile.ts +0 -144
  413. package/src/memory/service.ts +0 -144
  414. package/src/metrics/client.ts +0 -35
  415. package/src/metrics/event.ts +0 -43
  416. package/src/metrics/index.ts +0 -5
  417. package/src/metrics/installation.ts +0 -18
  418. package/src/metrics/subscriber.ts +0 -58
  419. package/src/metrics/util.ts +0 -9
  420. package/src/node.ts +0 -6
  421. package/src/npm/config.ts +0 -0
  422. package/src/npm/index.ts +0 -293
  423. package/src/npmcli-config.d.ts +0 -43
  424. package/src/patch/index.ts +0 -680
  425. package/src/permission/arity.ts +0 -163
  426. package/src/permission/evaluate.ts +0 -15
  427. package/src/permission/index.ts +0 -379
  428. package/src/permission/schema.ts +0 -17
  429. package/src/plugin/checkpoint-splitover.ts +0 -60
  430. package/src/plugin/cloudflare.ts +0 -76
  431. package/src/plugin/codex.ts +0 -607
  432. package/src/plugin/github-copilot/copilot.ts +0 -368
  433. package/src/plugin/github-copilot/models.ts +0 -153
  434. package/src/plugin/index.ts +0 -500
  435. package/src/plugin/install.ts +0 -439
  436. package/src/plugin/loader.ts +0 -216
  437. package/src/plugin/matcher.ts +0 -33
  438. package/src/plugin/meta.ts +0 -188
  439. package/src/plugin/shared.ts +0 -323
  440. package/src/plugin/subagent-progress-checker.ts +0 -147
  441. package/src/plugin/woozlit-free.ts +0 -164
  442. package/src/plugin/woozlit.ts +0 -440
  443. package/src/project/bootstrap.ts +0 -59
  444. package/src/project/index.ts +0 -2
  445. package/src/project/instance.ts +0 -190
  446. package/src/project/project-id.ts +0 -48
  447. package/src/project/project.sql.ts +0 -16
  448. package/src/project/project.ts +0 -501
  449. package/src/project/schema.ts +0 -15
  450. package/src/project/vcs.ts +0 -227
  451. package/src/provider/auth.ts +0 -234
  452. package/src/provider/error.ts +0 -216
  453. package/src/provider/index.ts +0 -5
  454. package/src/provider/models.ts +0 -180
  455. package/src/provider/provider.ts +0 -1788
  456. package/src/provider/schema.ts +0 -36
  457. package/src/provider/sdk/copilot/README.md +0 -5
  458. package/src/provider/sdk/copilot/chat/convert-to-openai-compatible-chat-messages.ts +0 -170
  459. package/src/provider/sdk/copilot/chat/get-response-metadata.ts +0 -15
  460. package/src/provider/sdk/copilot/chat/map-openai-compatible-finish-reason.ts +0 -19
  461. package/src/provider/sdk/copilot/chat/openai-compatible-api-types.ts +0 -64
  462. package/src/provider/sdk/copilot/chat/openai-compatible-chat-language-model.ts +0 -815
  463. package/src/provider/sdk/copilot/chat/openai-compatible-chat-options.ts +0 -28
  464. package/src/provider/sdk/copilot/chat/openai-compatible-metadata-extractor.ts +0 -44
  465. package/src/provider/sdk/copilot/chat/openai-compatible-prepare-tools.ts +0 -83
  466. package/src/provider/sdk/copilot/copilot-provider.ts +0 -100
  467. package/src/provider/sdk/copilot/index.ts +0 -2
  468. package/src/provider/sdk/copilot/openai-compatible-error.ts +0 -27
  469. package/src/provider/sdk/copilot/responses/convert-to-openai-responses-input.ts +0 -335
  470. package/src/provider/sdk/copilot/responses/map-openai-responses-finish-reason.ts +0 -22
  471. package/src/provider/sdk/copilot/responses/openai-config.ts +0 -18
  472. package/src/provider/sdk/copilot/responses/openai-error.ts +0 -22
  473. package/src/provider/sdk/copilot/responses/openai-responses-api-types.ts +0 -214
  474. package/src/provider/sdk/copilot/responses/openai-responses-language-model.ts +0 -1770
  475. package/src/provider/sdk/copilot/responses/openai-responses-prepare-tools.ts +0 -173
  476. package/src/provider/sdk/copilot/responses/openai-responses-settings.ts +0 -1
  477. package/src/provider/sdk/copilot/responses/tool/code-interpreter.ts +0 -87
  478. package/src/provider/sdk/copilot/responses/tool/file-search.ts +0 -127
  479. package/src/provider/sdk/copilot/responses/tool/image-generation.ts +0 -114
  480. package/src/provider/sdk/copilot/responses/tool/local-shell.ts +0 -64
  481. package/src/provider/sdk/copilot/responses/tool/web-search-preview.ts +0 -103
  482. package/src/provider/sdk/copilot/responses/tool/web-search.ts +0 -102
  483. package/src/provider/transform.ts +0 -1350
  484. package/src/pty/index.ts +0 -364
  485. package/src/pty/pty.bun.ts +0 -26
  486. package/src/pty/pty.node.ts +0 -27
  487. package/src/pty/pty.ts +0 -25
  488. package/src/pty/schema.ts +0 -17
  489. package/src/question/index.ts +0 -252
  490. package/src/question/schema.ts +0 -17
  491. package/src/server/adapter.bun.ts +0 -40
  492. package/src/server/adapter.node.ts +0 -66
  493. package/src/server/adapter.ts +0 -21
  494. package/src/server/error.ts +0 -53
  495. package/src/server/event.ts +0 -7
  496. package/src/server/fence.ts +0 -81
  497. package/src/server/mdns.ts +0 -60
  498. package/src/server/middleware.ts +0 -92
  499. package/src/server/projectors.ts +0 -28
  500. package/src/server/proxy.ts +0 -171
  501. package/src/server/routes/control/index.ts +0 -218
  502. package/src/server/routes/control/workspace.ts +0 -203
  503. package/src/server/routes/global.ts +0 -287
  504. package/src/server/routes/instance/bash-interactive.ts +0 -82
  505. package/src/server/routes/instance/config.ts +0 -89
  506. package/src/server/routes/instance/event.ts +0 -88
  507. package/src/server/routes/instance/experimental.ts +0 -408
  508. package/src/server/routes/instance/file.ts +0 -190
  509. package/src/server/routes/instance/httpapi/config.ts +0 -51
  510. package/src/server/routes/instance/httpapi/permission.ts +0 -72
  511. package/src/server/routes/instance/httpapi/project.ts +0 -62
  512. package/src/server/routes/instance/httpapi/provider.ts +0 -150
  513. package/src/server/routes/instance/httpapi/question.ts +0 -121
  514. package/src/server/routes/instance/httpapi/server.ts +0 -136
  515. package/src/server/routes/instance/index.ts +0 -301
  516. package/src/server/routes/instance/mcp.ts +0 -260
  517. package/src/server/routes/instance/middleware.ts +0 -35
  518. package/src/server/routes/instance/permission.ts +0 -73
  519. package/src/server/routes/instance/project.ts +0 -122
  520. package/src/server/routes/instance/provider.ts +0 -158
  521. package/src/server/routes/instance/pty.ts +0 -247
  522. package/src/server/routes/instance/question.ts +0 -162
  523. package/src/server/routes/instance/session.ts +0 -1296
  524. package/src/server/routes/instance/sync.ts +0 -143
  525. package/src/server/routes/instance/trace.ts +0 -59
  526. package/src/server/routes/instance/tui.ts +0 -384
  527. package/src/server/routes/instance/workflows.ts +0 -72
  528. package/src/server/routes/ui.ts +0 -55
  529. package/src/server/server.ts +0 -136
  530. package/src/server/workspace.ts +0 -122
  531. package/src/session/auto-dream.ts +0 -123
  532. package/src/session/boundary.ts +0 -77
  533. package/src/session/budgeted-read.ts +0 -118
  534. package/src/session/checkpoint-align.ts +0 -29
  535. package/src/session/checkpoint-context.ts +0 -36
  536. package/src/session/checkpoint-paths.ts +0 -86
  537. package/src/session/checkpoint-progress-reconcile.ts +0 -111
  538. package/src/session/checkpoint-retry.ts +0 -192
  539. package/src/session/checkpoint-templates.ts +0 -114
  540. package/src/session/checkpoint-validator.ts +0 -259
  541. package/src/session/checkpoint.ts +0 -1478
  542. package/src/session/classify.ts +0 -92
  543. package/src/session/claude-import.sql.ts +0 -13
  544. package/src/session/claude-import.ts +0 -379
  545. package/src/session/compaction.ts +0 -543
  546. package/src/session/goal.ts +0 -232
  547. package/src/session/index.ts +0 -1
  548. package/src/session/instruction.ts +0 -314
  549. package/src/session/last-message-info.ts +0 -32
  550. package/src/session/llm-request-prefix.ts +0 -82
  551. package/src/session/llm.ts +0 -735
  552. package/src/session/max-mode.ts +0 -397
  553. package/src/session/message-v2.ts +0 -1136
  554. package/src/session/message.ts +0 -191
  555. package/src/session/overflow.ts +0 -53
  556. package/src/session/prefix-capture-ref.ts +0 -48
  557. package/src/session/processor.ts +0 -972
  558. package/src/session/projectors.ts +0 -137
  559. package/src/session/prompt/anthropic.txt +0 -154
  560. package/src/session/prompt/beast.txt +0 -155
  561. package/src/session/prompt/build-switch.txt +0 -5
  562. package/src/session/prompt/codex.txt +0 -79
  563. package/src/session/prompt/compose.txt +0 -115
  564. package/src/session/prompt/copilot-gpt-5.txt +0 -143
  565. package/src/session/prompt/default.txt +0 -151
  566. package/src/session/prompt/gemini.txt +0 -155
  567. package/src/session/prompt/gpt.txt +0 -107
  568. package/src/session/prompt/kimi.txt +0 -95
  569. package/src/session/prompt/max-steps.txt +0 -16
  570. package/src/session/prompt/trinity.txt +0 -97
  571. package/src/session/prompt.ts +0 -3362
  572. package/src/session/prune.ts +0 -481
  573. package/src/session/retry.ts +0 -166
  574. package/src/session/revert.ts +0 -161
  575. package/src/session/run-state.ts +0 -135
  576. package/src/session/schema.ts +0 -36
  577. package/src/session/session.sql.ts +0 -110
  578. package/src/session/session.ts +0 -908
  579. package/src/session/status.ts +0 -89
  580. package/src/session/summary.ts +0 -163
  581. package/src/session/system.ts +0 -86
  582. package/src/session/todo.ts +0 -77
  583. package/src/share/index.ts +0 -2
  584. package/src/share/session.ts +0 -57
  585. package/src/share/share-next.ts +0 -381
  586. package/src/share/share.sql.ts +0 -13
  587. package/src/shell/shell.ts +0 -110
  588. package/src/skill/compose/.bundle/ask/SKILL.md +0 -58
  589. package/src/skill/compose/.bundle/brainstorm/SKILL.md +0 -220
  590. package/src/skill/compose/.bundle/brainstorm/scripts/frame-template.html +0 -214
  591. package/src/skill/compose/.bundle/brainstorm/scripts/helper.js +0 -88
  592. package/src/skill/compose/.bundle/brainstorm/scripts/server.cjs +0 -354
  593. package/src/skill/compose/.bundle/brainstorm/scripts/start-server.sh +0 -148
  594. package/src/skill/compose/.bundle/brainstorm/scripts/stop-server.sh +0 -56
  595. package/src/skill/compose/.bundle/brainstorm/spec-document-reviewer-prompt.md +0 -50
  596. package/src/skill/compose/.bundle/brainstorm/visual-companion.md +0 -287
  597. package/src/skill/compose/.bundle/debug/CREATION-LOG.md +0 -119
  598. package/src/skill/compose/.bundle/debug/SKILL.md +0 -297
  599. package/src/skill/compose/.bundle/debug/condition-based-waiting-example.ts +0 -158
  600. package/src/skill/compose/.bundle/debug/condition-based-waiting.md +0 -115
  601. package/src/skill/compose/.bundle/debug/defense-in-depth.md +0 -122
  602. package/src/skill/compose/.bundle/debug/find-polluter.sh +0 -63
  603. package/src/skill/compose/.bundle/debug/root-cause-tracing.md +0 -169
  604. package/src/skill/compose/.bundle/debug/test-academic.md +0 -14
  605. package/src/skill/compose/.bundle/debug/test-pressure-1.md +0 -58
  606. package/src/skill/compose/.bundle/debug/test-pressure-2.md +0 -68
  607. package/src/skill/compose/.bundle/debug/test-pressure-3.md +0 -69
  608. package/src/skill/compose/.bundle/execute/SKILL.md +0 -71
  609. package/src/skill/compose/.bundle/feedback/SKILL.md +0 -214
  610. package/src/skill/compose/.bundle/merge/SKILL.md +0 -252
  611. package/src/skill/compose/.bundle/new-skill/SKILL.md +0 -656
  612. package/src/skill/compose/.bundle/new-skill/anthropic-best-practices.md +0 -1150
  613. package/src/skill/compose/.bundle/new-skill/examples/CLAUDE_MD_TESTING.md +0 -189
  614. package/src/skill/compose/.bundle/new-skill/graphviz-conventions.dot +0 -172
  615. package/src/skill/compose/.bundle/new-skill/persuasion-principles.md +0 -187
  616. package/src/skill/compose/.bundle/new-skill/render-graphs.js +0 -168
  617. package/src/skill/compose/.bundle/new-skill/testing-skills-with-subagents.md +0 -384
  618. package/src/skill/compose/.bundle/parallel/SKILL.md +0 -182
  619. package/src/skill/compose/.bundle/plan/SKILL.md +0 -161
  620. package/src/skill/compose/.bundle/plan/plan-document-reviewer-prompt.md +0 -50
  621. package/src/skill/compose/.bundle/report/SKILL.md +0 -180
  622. package/src/skill/compose/.bundle/review/SKILL.md +0 -104
  623. package/src/skill/compose/.bundle/review/code-reviewer.md +0 -171
  624. package/src/skill/compose/.bundle/subagent/SKILL.md +0 -344
  625. package/src/skill/compose/.bundle/subagent/code-quality-reviewer-prompt.md +0 -24
  626. package/src/skill/compose/.bundle/subagent/implementer-prompt.md +0 -126
  627. package/src/skill/compose/.bundle/subagent/spec-reviewer-prompt.md +0 -112
  628. package/src/skill/compose/.bundle/tdd/SKILL.md +0 -372
  629. package/src/skill/compose/.bundle/tdd/testing-anti-patterns.md +0 -299
  630. package/src/skill/compose/.bundle/verify/SKILL.md +0 -140
  631. package/src/skill/compose/.bundle/worktree/SKILL.md +0 -234
  632. package/src/skill/compose/LICENSE-karpathy +0 -28
  633. package/src/skill/compose/bundle.macro.ts +0 -30
  634. package/src/skill/compose/extract.ts +0 -85
  635. package/src/skill/discovery.ts +0 -116
  636. package/src/skill/index.ts +0 -311
  637. package/src/snapshot/index.ts +0 -777
  638. package/src/sql.d.ts +0 -4
  639. package/src/storage/db.bun.ts +0 -8
  640. package/src/storage/db.node.ts +0 -8
  641. package/src/storage/db.ts +0 -172
  642. package/src/storage/index.ts +0 -26
  643. package/src/storage/json-migration.ts +0 -426
  644. package/src/storage/schema.sql.ts +0 -10
  645. package/src/storage/schema.ts +0 -7
  646. package/src/storage/storage.ts +0 -331
  647. package/src/sync/README.md +0 -179
  648. package/src/sync/event.sql.ts +0 -16
  649. package/src/sync/index.ts +0 -278
  650. package/src/sync/schema.ts +0 -14
  651. package/src/task/events.ts +0 -28
  652. package/src/task/gate-state.ts +0 -54
  653. package/src/task/gate.ts +0 -116
  654. package/src/task/index.ts +0 -1
  655. package/src/task/registry.ts +0 -387
  656. package/src/task/schema.ts +0 -43
  657. package/src/task/task.sql.ts +0 -50
  658. package/src/team/events.ts +0 -22
  659. package/src/team/index.ts +0 -113
  660. package/src/team/schema.ts +0 -31
  661. package/src/temporary.ts +0 -33
  662. package/src/tool/actor.shell.txt +0 -72
  663. package/src/tool/actor.ts +0 -803
  664. package/src/tool/actor.txt +0 -103
  665. package/src/tool/apply_patch.ts +0 -308
  666. package/src/tool/apply_patch.txt +0 -33
  667. package/src/tool/bash-interactive.ts +0 -183
  668. package/src/tool/bash.ts +0 -696
  669. package/src/tool/bash.txt +0 -123
  670. package/src/tool/change-directory.ts +0 -91
  671. package/src/tool/codesearch.ts +0 -63
  672. package/src/tool/codesearch.txt +0 -12
  673. package/src/tool/edit.ts +0 -685
  674. package/src/tool/edit.txt +0 -10
  675. package/src/tool/external-directory.ts +0 -132
  676. package/src/tool/glob.ts +0 -100
  677. package/src/tool/glob.txt +0 -6
  678. package/src/tool/grep.ts +0 -145
  679. package/src/tool/grep.txt +0 -8
  680. package/src/tool/history.ts +0 -146
  681. package/src/tool/history.txt +0 -17
  682. package/src/tool/index.ts +0 -4
  683. package/src/tool/invalid.ts +0 -20
  684. package/src/tool/invocation-style.ts +0 -17
  685. package/src/tool/lsp.ts +0 -91
  686. package/src/tool/lsp.txt +0 -19
  687. package/src/tool/mcp-exa.ts +0 -78
  688. package/src/tool/memory-path-guard.ts +0 -162
  689. package/src/tool/memory.ts +0 -81
  690. package/src/tool/memory.txt +0 -69
  691. package/src/tool/multiedit.ts +0 -61
  692. package/src/tool/multiedit.txt +0 -41
  693. package/src/tool/plan-enter.txt +0 -14
  694. package/src/tool/plan-exit.txt +0 -13
  695. package/src/tool/plan.ts +0 -90
  696. package/src/tool/question.ts +0 -67
  697. package/src/tool/question.txt +0 -10
  698. package/src/tool/read.ts +0 -327
  699. package/src/tool/read.txt +0 -14
  700. package/src/tool/registry.ts +0 -415
  701. package/src/tool/schema.ts +0 -17
  702. package/src/tool/session-cwd.ts +0 -35
  703. package/src/tool/shell-tokenize.ts +0 -346
  704. package/src/tool/shell-wrap.ts +0 -190
  705. package/src/tool/skill.ts +0 -76
  706. package/src/tool/skill.txt +0 -5
  707. package/src/tool/task.shell.txt +0 -57
  708. package/src/tool/task.ts +0 -456
  709. package/src/tool/task.txt +0 -56
  710. package/src/tool/tool.ts +0 -153
  711. package/src/tool/truncate.ts +0 -201
  712. package/src/tool/truncation-dir.ts +0 -4
  713. package/src/tool/webfetch.ts +0 -199
  714. package/src/tool/webfetch.txt +0 -13
  715. package/src/tool/websearch/index.ts +0 -111
  716. package/src/tool/websearch/mimo.ts +0 -120
  717. package/src/tool/websearch/websearch.txt +0 -14
  718. package/src/tool/workflow.ts +0 -164
  719. package/src/tool/workflow.txt +0 -25
  720. package/src/tool/write.ts +0 -88
  721. package/src/tool/write.txt +0 -9
  722. package/src/util/abort.ts +0 -35
  723. package/src/util/archive.ts +0 -15
  724. package/src/util/color.ts +0 -17
  725. package/src/util/data-url.ts +0 -9
  726. package/src/util/defer.ts +0 -10
  727. package/src/util/effect-http-client.ts +0 -11
  728. package/src/util/effect-zod.ts +0 -367
  729. package/src/util/error.ts +0 -78
  730. package/src/util/filesystem.ts +0 -243
  731. package/src/util/fn.ts +0 -21
  732. package/src/util/format.ts +0 -20
  733. package/src/util/iife.ts +0 -3
  734. package/src/util/index.ts +0 -12
  735. package/src/util/keybind.ts +0 -101
  736. package/src/util/lazy.ts +0 -18
  737. package/src/util/local-context.ts +0 -23
  738. package/src/util/locale.ts +0 -79
  739. package/src/util/lock.ts +0 -96
  740. package/src/util/log.ts +0 -197
  741. package/src/util/media.ts +0 -26
  742. package/src/util/mimo-process.ts +0 -24
  743. package/src/util/network.ts +0 -9
  744. package/src/util/process.ts +0 -174
  745. package/src/util/queue.ts +0 -32
  746. package/src/util/record.ts +0 -3
  747. package/src/util/rpc.ts +0 -64
  748. package/src/util/schema.ts +0 -53
  749. package/src/util/scrap.ts +0 -10
  750. package/src/util/signal.ts +0 -12
  751. package/src/util/timeout.ts +0 -14
  752. package/src/util/token.ts +0 -5
  753. package/src/util/update-schema.ts +0 -13
  754. package/src/util/which.ts +0 -14
  755. package/src/util/wildcard.ts +0 -57
  756. package/src/workflow/builtin/deep-research.js +0 -391
  757. package/src/workflow/builtin.ts +0 -54
  758. package/src/workflow/events.ts +0 -72
  759. package/src/workflow/meta.ts +0 -335
  760. package/src/workflow/persistence.ts +0 -312
  761. package/src/workflow/resolve.ts +0 -45
  762. package/src/workflow/runtime-ref.ts +0 -18
  763. package/src/workflow/runtime.ts +0 -1234
  764. package/src/workflow/sandbox.ts +0 -280
  765. package/src/workflow/workflow.sql.ts +0 -31
  766. package/src/workflow/workspace.ts +0 -69
  767. package/src/worktree/index.ts +0 -614
  768. package/sst-env.d.ts +0 -10
  769. package/test/AGENTS.md +0 -133
  770. package/test/account/repo.test.ts +0 -352
  771. package/test/account/service.test.ts +0 -456
  772. package/test/acp/agent-interface.test.ts +0 -51
  773. package/test/acp/event-subscription.test.ts +0 -725
  774. package/test/actor/cancel-cascade.test.ts +0 -432
  775. package/test/actor/no-completion-listener.test.ts +0 -41
  776. package/test/actor/poststop-progress-write-permission.repro.test.ts +0 -414
  777. package/test/actor/registry-render.test.ts +0 -113
  778. package/test/actor/registry-status.test.ts +0 -111
  779. package/test/actor/registry.test.ts +0 -619
  780. package/test/actor/return-header.test.ts +0 -40
  781. package/test/actor/spawn-lifecycle.test.ts +0 -346
  782. package/test/actor/spawn-no-deadlock.test.ts +0 -340
  783. package/test/actor/spawn-notification.test.ts +0 -393
  784. package/test/actor/spawn-task-autostart.test.ts +0 -530
  785. package/test/actor/spawn.test.ts +0 -1072
  786. package/test/actor/status-event-payload.test.ts +0 -132
  787. package/test/actor/terminology.test.ts +0 -39
  788. package/test/actor/turn.test.ts +0 -125
  789. package/test/actor/waiter.test.ts +0 -246
  790. package/test/agent/agent.test.ts +0 -874
  791. package/test/agent/allowlist.test.ts +0 -45
  792. package/test/auth/auth.test.ts +0 -86
  793. package/test/bus/bus-effect.test.ts +0 -162
  794. package/test/bus/bus-integration.test.ts +0 -87
  795. package/test/bus/bus.test.ts +0 -219
  796. package/test/cli/account.test.ts +0 -26
  797. package/test/cli/cmd/tui/prompt-part.test.ts +0 -47
  798. package/test/cli/error.test.ts +0 -18
  799. package/test/cli/github-action.test.ts +0 -198
  800. package/test/cli/github-remote.test.ts +0 -80
  801. package/test/cli/import.test.ts +0 -54
  802. package/test/cli/plugin-auth-picker.test.ts +0 -120
  803. package/test/cli/run-completion.test.ts +0 -131
  804. package/test/cli/tui/keybind-plugin.test.ts +0 -90
  805. package/test/cli/tui/plugin-add.test.ts +0 -111
  806. package/test/cli/tui/plugin-install.test.ts +0 -87
  807. package/test/cli/tui/plugin-lifecycle.test.ts +0 -224
  808. package/test/cli/tui/plugin-loader-entrypoint.test.ts +0 -484
  809. package/test/cli/tui/plugin-loader-pure.test.ts +0 -71
  810. package/test/cli/tui/plugin-loader.test.ts +0 -816
  811. package/test/cli/tui/plugin-toggle.test.ts +0 -157
  812. package/test/cli/tui/revert-diff.test.ts +0 -35
  813. package/test/cli/tui/route-agent-id.test.ts +0 -26
  814. package/test/cli/tui/sidebar-tps.test.ts +0 -63
  815. package/test/cli/tui/slot-replace.test.tsx +0 -47
  816. package/test/cli/tui/sync-bucket.test.ts +0 -29
  817. package/test/cli/tui/theme-store.test.ts +0 -51
  818. package/test/cli/tui/thread.test.ts +0 -121
  819. package/test/cli/tui/transcript.test.ts +0 -426
  820. package/test/cli/tui/use-event.test.tsx +0 -175
  821. package/test/cli/tui/voice.test.ts +0 -269
  822. package/test/command/deep-research-command.test.ts +0 -16
  823. package/test/config/agent-color.test.ts +0 -77
  824. package/test/config/checkpoint-fork.test.ts +0 -21
  825. package/test/config/config.test.ts +0 -2577
  826. package/test/config/fixtures/empty-frontmatter.md +0 -4
  827. package/test/config/fixtures/frontmatter.md +0 -28
  828. package/test/config/fixtures/markdown-header.md +0 -11
  829. package/test/config/fixtures/no-frontmatter.md +0 -1
  830. package/test/config/fixtures/weird-model-id.md +0 -13
  831. package/test/config/lsp.test.ts +0 -87
  832. package/test/config/markdown.test.ts +0 -228
  833. package/test/config/plugin.test.ts +0 -0
  834. package/test/config/tui.test.ts +0 -627
  835. package/test/control-plane/adaptors.test.ts +0 -71
  836. package/test/control-plane/sse.test.ts +0 -56
  837. package/test/effect/app-runtime-logger.test.ts +0 -92
  838. package/test/effect/cross-spawn-spawner.test.ts +0 -411
  839. package/test/effect/instance-state.test.ts +0 -482
  840. package/test/effect/observability.test.ts +0 -46
  841. package/test/effect/run-service.test.ts +0 -46
  842. package/test/effect/runner-warn-log.test.ts +0 -111
  843. package/test/effect/runner.test.ts +0 -494
  844. package/test/fake/provider.ts +0 -90
  845. package/test/file/fsmonitor.test.ts +0 -68
  846. package/test/file/ignore.test.ts +0 -10
  847. package/test/file/index.test.ts +0 -956
  848. package/test/file/path-traversal.test.ts +0 -204
  849. package/test/file/ripgrep.test.ts +0 -214
  850. package/test/file/watcher.test.ts +0 -249
  851. package/test/filesystem/filesystem.test.ts +0 -319
  852. package/test/fixture/db.ts +0 -11
  853. package/test/fixture/fixture.test.ts +0 -58
  854. package/test/fixture/fixture.ts +0 -190
  855. package/test/fixture/flock-worker.ts +0 -72
  856. package/test/fixture/lsp/fake-lsp-server.js +0 -75
  857. package/test/fixture/plug-worker.ts +0 -93
  858. package/test/fixture/plugin-meta-worker.ts +0 -19
  859. package/test/fixture/skills/agents-sdk/SKILL.md +0 -152
  860. package/test/fixture/skills/agents-sdk/references/callable.md +0 -92
  861. package/test/fixture/skills/cloudflare/SKILL.md +0 -211
  862. package/test/fixture/skills/index.json +0 -6
  863. package/test/fixture/tui-plugin.ts +0 -329
  864. package/test/fixture/tui-runtime.ts +0 -31
  865. package/test/format/format.test.ts +0 -244
  866. package/test/git/git.test.ts +0 -128
  867. package/test/global/fixture/global-paths-worker.ts +0 -17
  868. package/test/global/mimocode-home.test.ts +0 -143
  869. package/test/history/backfill.test.ts +0 -149
  870. package/test/history/extract.test.ts +0 -106
  871. package/test/history/fts-query.test.ts +0 -30
  872. package/test/history/resolve.test.ts +0 -130
  873. package/test/history/service.test.ts +0 -210
  874. package/test/history/writer.test.ts +0 -163
  875. package/test/ide/ide.test.ts +0 -82
  876. package/test/inbox/drain-in-loop.test.ts +0 -230
  877. package/test/inbox/fork-agent-compat.test.ts +0 -387
  878. package/test/inbox/gc-on-init.test.ts +0 -167
  879. package/test/inbox/send-no-block.test.ts +0 -120
  880. package/test/inbox/sender-cancel-independence.test.ts +0 -160
  881. package/test/inbox/wake-matrix.test.ts +0 -141
  882. package/test/installation/installation.test.ts +0 -226
  883. package/test/keybind.test.ts +0 -421
  884. package/test/lib/effect.ts +0 -53
  885. package/test/lib/filesystem.ts +0 -10
  886. package/test/lib/llm-server.ts +0 -770
  887. package/test/lib/scripted-llm-server.ts +0 -245
  888. package/test/lsp/client.test.ts +0 -98
  889. package/test/lsp/index.test.ts +0 -109
  890. package/test/lsp/launch.test.ts +0 -22
  891. package/test/lsp/lifecycle.test.ts +0 -184
  892. package/test/mcp/headers.test.ts +0 -178
  893. package/test/mcp/lifecycle.test.ts +0 -824
  894. package/test/mcp/oauth-auto-connect.test.ts +0 -281
  895. package/test/mcp/oauth-browser.test.ts +0 -268
  896. package/test/mcp/oauth-callback.test.ts +0 -34
  897. package/test/memory/abort-leak-webfetch.ts +0 -49
  898. package/test/memory/abort-leak.test.ts +0 -127
  899. package/test/memory/cc-frontmatter.test.ts +0 -85
  900. package/test/memory/cc-paths.test.ts +0 -60
  901. package/test/memory/cc-reconcile.test.ts +0 -239
  902. package/test/memory/cc-search.test.ts +0 -151
  903. package/test/memory/fts-query.test.ts +0 -48
  904. package/test/memory/fts-rowid-stability.test.ts +0 -271
  905. package/test/memory/paths.test.ts +0 -210
  906. package/test/memory/reconcile.test.ts +0 -115
  907. package/test/memory/service.test.ts +0 -169
  908. package/test/npm.test.ts +0 -18
  909. package/test/patch/patch.test.ts +0 -348
  910. package/test/permission/abort.test.ts +0 -116
  911. package/test/permission/arity.test.ts +0 -33
  912. package/test/permission/disabled.test.ts +0 -51
  913. package/test/permission/next.test.ts +0 -1080
  914. package/test/permission/non-interactive.test.ts +0 -55
  915. package/test/permission-task.test.ts +0 -326
  916. package/test/plugin/actor-hooks.test.ts +0 -1471
  917. package/test/plugin/auth-override.test.ts +0 -79
  918. package/test/plugin/checkpoint-splitover.test.ts +0 -434
  919. package/test/plugin/cloudflare.test.ts +0 -68
  920. package/test/plugin/codex.test.ts +0 -123
  921. package/test/plugin/github-copilot-models.test.ts +0 -163
  922. package/test/plugin/install-concurrency.test.ts +0 -140
  923. package/test/plugin/install.test.ts +0 -570
  924. package/test/plugin/loader-shared.test.ts +0 -1169
  925. package/test/plugin/matcher.test.ts +0 -97
  926. package/test/plugin/meta.test.ts +0 -137
  927. package/test/plugin/shared.test.ts +0 -88
  928. package/test/plugin/subagent-progress-checker.test.ts +0 -227
  929. package/test/plugin/trigger.test.ts +0 -116
  930. package/test/plugin/woozlit.test.ts +0 -68
  931. package/test/plugin/workspace-adaptor.test.ts +0 -109
  932. package/test/preload.ts +0 -102
  933. package/test/project/migrate-global.test.ts +0 -150
  934. package/test/project/project-id.test.ts +0 -64
  935. package/test/project/project.test.ts +0 -481
  936. package/test/project/vcs.test.ts +0 -286
  937. package/test/project/worktree-remove.test.ts +0 -126
  938. package/test/project/worktree.test.ts +0 -214
  939. package/test/provider/amazon-bedrock.test.ts +0 -462
  940. package/test/provider/copilot/convert-to-copilot-messages.test.ts +0 -523
  941. package/test/provider/copilot/copilot-chat-model.test.ts +0 -592
  942. package/test/provider/error.test.ts +0 -160
  943. package/test/provider/gitlab-duo.test.ts +0 -413
  944. package/test/provider/model-groups.test.ts +0 -389
  945. package/test/provider/provider-chunk-timeout.test.ts +0 -23
  946. package/test/provider/provider.test.ts +0 -2648
  947. package/test/provider/transform.test.ts +0 -3379
  948. package/test/pty/pty-output-isolation.test.ts +0 -146
  949. package/test/pty/pty-session.test.ts +0 -102
  950. package/test/pty/pty-shell.test.ts +0 -69
  951. package/test/question/question.test.ts +0 -464
  952. package/test/server/global-session-list.test.ts +0 -105
  953. package/test/server/project-init-git.test.ts +0 -122
  954. package/test/server/session-actions.test.ts +0 -49
  955. package/test/server/session-list.test.ts +0 -110
  956. package/test/server/session-messages.test.ts +0 -220
  957. package/test/server/session-prompt-busy.test.ts +0 -146
  958. package/test/server/session-select.test.ts +0 -100
  959. package/test/server/session-task-route.test.ts +0 -165
  960. package/test/server/summarize-route-main-slice.test.ts +0 -99
  961. package/test/server/trace-attributes.test.ts +0 -76
  962. package/test/server/workflows-route.test.ts +0 -279
  963. package/test/session/bootstrap-skip-system.test.ts +0 -121
  964. package/test/session/boundary.test.ts +0 -33
  965. package/test/session/budgeted-read.test.ts +0 -74
  966. package/test/session/checkpoint-align.test.ts +0 -58
  967. package/test/session/checkpoint-boundary.test.ts +0 -186
  968. package/test/session/checkpoint-child-session.test.ts +0 -508
  969. package/test/session/checkpoint-context.test.ts +0 -141
  970. package/test/session/checkpoint-drain.test.ts +0 -188
  971. package/test/session/checkpoint-extract-titles.test.ts +0 -58
  972. package/test/session/checkpoint-fork-mode.test.ts +0 -576
  973. package/test/session/checkpoint-main-slice.test.ts +0 -259
  974. package/test/session/checkpoint-paths.test.ts +0 -78
  975. package/test/session/checkpoint-permission.test.ts +0 -136
  976. package/test/session/checkpoint-progress-reconcile.test.ts +0 -219
  977. package/test/session/checkpoint-rebuild-unify.test.ts +0 -143
  978. package/test/session/checkpoint-rebuild-v3.test.ts +0 -248
  979. package/test/session/checkpoint-render-verify.test.ts +0 -512
  980. package/test/session/checkpoint-retry.test.ts +0 -150
  981. package/test/session/checkpoint-splitover-integration.test.ts +0 -533
  982. package/test/session/checkpoint-templates.test.ts +0 -51
  983. package/test/session/checkpoint-thresholds.test.ts +0 -120
  984. package/test/session/checkpoint-validator.test.ts +0 -189
  985. package/test/session/classify-integration.test.ts +0 -476
  986. package/test/session/classify.test.ts +0 -335
  987. package/test/session/compaction-agent-scope.test.ts +0 -164
  988. package/test/session/context-inheritance.test.ts +0 -46
  989. package/test/session/fork-prefix-invariant.test.ts +0 -116
  990. package/test/session/goal.test.ts +0 -106
  991. package/test/session/instruction.test.ts +0 -387
  992. package/test/session/invalid-output-continuation.test.ts +0 -150
  993. package/test/session/last-message-info.test.ts +0 -47
  994. package/test/session/length-tool-safety.test.ts +0 -121
  995. package/test/session/llm-request-prefix.test.ts +0 -197
  996. package/test/session/llm-retry.test.ts +0 -59
  997. package/test/session/llm-system-prompt.test.ts +0 -479
  998. package/test/session/llm.test.ts +0 -1272
  999. package/test/session/main-lifecycle.test.ts +0 -51
  1000. package/test/session/main-runloop-history-invariant.test.ts +0 -182
  1001. package/test/session/max-mode-econnreset.test.ts +0 -229
  1002. package/test/session/max-mode.test.ts +0 -54
  1003. package/test/session/message-v2-filter.test.ts +0 -197
  1004. package/test/session/message-v2.test.ts +0 -1119
  1005. package/test/session/messages-default-main.test.ts +0 -105
  1006. package/test/session/messages-pagination.test.ts +0 -888
  1007. package/test/session/overflow.test.ts +0 -576
  1008. package/test/session/processor-effect.test.ts +0 -853
  1009. package/test/session/prompt-effect.test.ts +0 -1574
  1010. package/test/session/prompt-rebuild-loop.test.ts +0 -108
  1011. package/test/session/prompt-rebuild-reset.test.ts +0 -67
  1012. package/test/session/prompt-sweep.test.ts +0 -145
  1013. package/test/session/prompt-task-gate.test.ts +0 -127
  1014. package/test/session/prompt.test.ts +0 -703
  1015. package/test/session/prune-main-slice.test.ts +0 -272
  1016. package/test/session/prune-skip-system.test.ts +0 -346
  1017. package/test/session/prune.test.ts +0 -419
  1018. package/test/session/rebuild-microcompact.test.ts +0 -318
  1019. package/test/session/recall-reminder.test.ts +0 -37
  1020. package/test/session/retry.test.ts +0 -410
  1021. package/test/session/revert-compact.test.ts +0 -639
  1022. package/test/session/run-state-tuple-key.test.ts +0 -152
  1023. package/test/session/session-create-registers-main.test.ts +0 -70
  1024. package/test/session/session.test.ts +0 -181
  1025. package/test/session/snapshot-tool-race.test.ts +0 -301
  1026. package/test/session/structured-output-integration.test.ts +0 -264
  1027. package/test/session/structured-output-retry.test.ts +0 -127
  1028. package/test/session/structured-output.test.ts +0 -397
  1029. package/test/session/summary-main-slice.test.ts +0 -170
  1030. package/test/session/system.test.ts +0 -72
  1031. package/test/share/share-next.test.ts +0 -332
  1032. package/test/shell/shell.test.ts +0 -73
  1033. package/test/skill/compose-review.test.ts +0 -141
  1034. package/test/skill/discovery.test.ts +0 -116
  1035. package/test/skill/skill.test.ts +0 -465
  1036. package/test/snapshot/snapshot.test.ts +0 -1531
  1037. package/test/storage/db.test.ts +0 -16
  1038. package/test/storage/json-migration.test.ts +0 -831
  1039. package/test/storage/storage.test.ts +0 -293
  1040. package/test/sync/index.test.ts +0 -237
  1041. package/test/task/gate-state.test.ts +0 -66
  1042. package/test/task/gate.test.ts +0 -167
  1043. package/test/task/registry.test.ts +0 -152
  1044. package/test/task/state-machine.test.ts +0 -292
  1045. package/test/team/migrate-to-inbox.test.ts +0 -124
  1046. package/test/team/team.test.ts +0 -75
  1047. package/test/tool/__snapshots__/tool.test.ts.snap +0 -9
  1048. package/test/tool/actor-cancel.test.ts +0 -206
  1049. package/test/tool/actor-recover.test.ts +0 -50
  1050. package/test/tool/actor-send.test.ts +0 -200
  1051. package/test/tool/actor-status.test.ts +0 -296
  1052. package/test/tool/actor-wait.test.ts +0 -193
  1053. package/test/tool/actor.shell.test.ts +0 -250
  1054. package/test/tool/actor.test.ts +0 -748
  1055. package/test/tool/apply_patch.test.ts +0 -626
  1056. package/test/tool/bash.test.ts +0 -1195
  1057. package/test/tool/describe-workflow.test.ts +0 -12
  1058. package/test/tool/edit.test.ts +0 -691
  1059. package/test/tool/external-directory.test.ts +0 -207
  1060. package/test/tool/fixtures/large-image.png +0 -0
  1061. package/test/tool/fixtures/models-api.json +0 -65179
  1062. package/test/tool/glob.test.ts +0 -81
  1063. package/test/tool/grep.test.ts +0 -114
  1064. package/test/tool/history.test.ts +0 -144
  1065. package/test/tool/invocation-style.test.ts +0 -30
  1066. package/test/tool/memory-edit-ask-skip.test.ts +0 -62
  1067. package/test/tool/memory-path-guard.test.ts +0 -594
  1068. package/test/tool/memory.test.ts +0 -71
  1069. package/test/tool/question.test.ts +0 -167
  1070. package/test/tool/read.test.ts +0 -483
  1071. package/test/tool/registry-invocation-style.test.ts +0 -121
  1072. package/test/tool/registry.test.ts +0 -164
  1073. package/test/tool/shell-tokenize.test.ts +0 -273
  1074. package/test/tool/shell-wrap-missing-script.test.ts +0 -128
  1075. package/test/tool/shell-wrap.test.ts +0 -257
  1076. package/test/tool/skill.test.ts +0 -99
  1077. package/test/tool/task-recover.test.ts +0 -36
  1078. package/test/tool/task.shell.test.ts +0 -234
  1079. package/test/tool/task.test.ts +0 -296
  1080. package/test/tool/tool-def-shell-shape.test.ts +0 -23
  1081. package/test/tool/tool-define.test.ts +0 -59
  1082. package/test/tool/truncation.test.ts +0 -253
  1083. package/test/tool/webfetch.test.ts +0 -103
  1084. package/test/tool/whitelist.test.ts +0 -373
  1085. package/test/tool/write.test.ts +0 -244
  1086. package/test/util/data-url.test.ts +0 -14
  1087. package/test/util/effect-zod.test.ts +0 -869
  1088. package/test/util/error.test.ts +0 -38
  1089. package/test/util/filesystem.test.ts +0 -656
  1090. package/test/util/format.test.ts +0 -59
  1091. package/test/util/glob.test.ts +0 -164
  1092. package/test/util/iife.test.ts +0 -36
  1093. package/test/util/lazy.test.ts +0 -50
  1094. package/test/util/lock.test.ts +0 -72
  1095. package/test/util/log.test.ts +0 -44
  1096. package/test/util/module.test.ts +0 -59
  1097. package/test/util/process.test.ts +0 -128
  1098. package/test/util/timeout.test.ts +0 -21
  1099. package/test/util/which.test.ts +0 -100
  1100. package/test/util/wildcard.test.ts +0 -90
  1101. package/test/workflow/builtin.test.ts +0 -22
  1102. package/test/workflow/deep-research-cluster.test.ts +0 -47
  1103. package/test/workflow/lib.ts +0 -243
  1104. package/test/workflow/meta.test.ts +0 -142
  1105. package/test/workflow/model-routing.test.ts +0 -68
  1106. package/test/workflow/persistence.test.ts +0 -229
  1107. package/test/workflow/resolve.test.ts +0 -37
  1108. package/test/workflow/runtime-nested.test.ts +0 -419
  1109. package/test/workflow/runtime-worktree.test.ts +0 -261
  1110. package/test/workflow/runtime.test.ts +0 -1078
  1111. package/test/workflow/sandbox.test.ts +0 -259
  1112. package/test/workflow/tool.test.ts +0 -473
  1113. package/test/workflow/verify-wow.test.ts +0 -144
  1114. package/test/workflow/workspace.test.ts +0 -88
  1115. package/test/workspace/workspace-restore.test.ts +0 -281
  1116. package/test/worktree/index.test.ts +0 -30
  1117. package/tsconfig.json +0 -24
  1118. /package/{script/postinstall.mjs → postinstall.mjs} +0 -0
@@ -1,1478 +0,0 @@
1
- import fs from "fs/promises"
2
- import path from "path"
3
- import { Global } from "@/global"
4
- import { Bus } from "@/bus"
5
- import { Config } from "@/config"
6
- import { Memory } from "@/memory"
7
- import { MemoryFtsTable } from "@/memory/fts.sql"
8
- import { TaskRegistry } from "@/task/registry"
9
- import { ActorRegistry } from "@/actor/registry"
10
- import type { AgentOutcome, ForkContext } from "@/actor/spawn"
11
- import { spawnRef } from "@/actor/spawn-ref"
12
- import { prefixCaptureRef } from "./prefix-capture-ref"
13
- import { Database, and, eq, or } from "@/storage"
14
- import { Instance } from "@/project/instance"
15
- import { ProjectID } from "@/project/schema"
16
- import { SessionTable } from "./session.sql"
17
- import * as Session from "./session"
18
- import { MessageV2 } from "./message-v2"
19
- import { SessionID, MessageID, PartID } from "./schema"
20
- import { Log, Token } from "../util"
21
- import { Effect, Layer, Deferred, Context, Scope } from "effect"
22
- import { makeRuntime } from "@/effect/run-service"
23
- import type { ActorPromptOps } from "@/tool/actor"
24
- import type { ProviderID, ModelID } from "../provider/schema"
25
- import PROMPT_CHECKPOINT_WRITER from "@/agent/prompt/checkpoint-writer.txt"
26
- import { WriterCachePerf } from "@/actor/events"
27
- import {
28
- metaDir,
29
- checkpointPath,
30
- memoryPath,
31
- notesPath,
32
- globalMemoryPath,
33
- migrateProjectMemory,
34
- } from "./checkpoint-paths"
35
- import { readBudgeted, readBudgetedSectionAware } from "./budgeted-read"
36
- import type { LastMessageInfo } from "./last-message-info"
37
- import { CHECKPOINT_TEMPLATE, MEMORY_TEMPLATE, NOTES_TEMPLATE, CHECKPOINT_SECTION_BUDGETS } from "./checkpoint-templates"
38
- import { adjustBoundaryForApiInvariants } from "./boundary"
39
- import { alignToNonToolResultUser } from "./checkpoint-align"
40
- import { loadPriorDiscoveredTitles } from "./checkpoint-retry"
41
- import * as CheckpointContext from "./checkpoint-context"
42
- import { buildProgressDiff } from "./checkpoint-progress-reconcile"
43
-
44
- const log = Log.create({ service: "session.checkpoint" })
45
-
46
- function truncate(s: string, max: number): string {
47
- return s.length <= max ? s : s.slice(0, max - 60) + "\n... (truncated, full body at file)"
48
- }
49
-
50
- function autonomousLoopReminder(): string {
51
- return [
52
- "<system-reminder>",
53
- "You are mid-loop in an autonomous task. Continue your work loop:",
54
- "respond to the tool results below and proceed to the next iteration.",
55
- "</system-reminder>",
56
- ].join("\n")
57
- }
58
-
59
- function stopReminder(focusTaskID: string | undefined): string {
60
- const taskHint = focusTaskID
61
- ? `Consult this session's tasks/${focusTaskID}/progress.md head section.`
62
- : "Consult the most recently active task's progress.md head section."
63
- return [
64
- "<system-reminder>",
65
- "The previous assistant turn ended with a stop. Before stopping again,",
66
- taskHint,
67
- "Compare the Task spec to the latest Progress entries. If the task is",
68
- "incomplete, proceed to the next concrete step. Only stop when the spec",
69
- "is genuinely satisfied or you need user input you cannot infer.",
70
- "</system-reminder>",
71
- ].join("\n")
72
- }
73
-
74
- function toolResultContinueReminder(): string {
75
- return [
76
- "<system-reminder>",
77
- "Tool results above are real history from the autonomous loop. Process",
78
- "them and continue to the next iteration. Do not pause to summarize.",
79
- "</system-reminder>",
80
- ].join("\n")
81
- }
82
-
83
- async function ensureCheckpointTemplate(checkpointFile: string): Promise<void> {
84
- if (!(await Bun.file(checkpointFile).exists())) {
85
- await fs.mkdir(path.dirname(checkpointFile), { recursive: true })
86
- await Bun.write(checkpointFile, CHECKPOINT_TEMPLATE)
87
- }
88
- }
89
-
90
- async function ensureMemoryTemplate(memoryFile: string): Promise<void> {
91
- if (!(await Bun.file(memoryFile).exists())) {
92
- await fs.mkdir(path.dirname(memoryFile), { recursive: true })
93
- await Bun.write(memoryFile, MEMORY_TEMPLATE)
94
- }
95
- }
96
-
97
- async function ensureNotesTemplate(notesFile: string): Promise<void> {
98
- if (!(await Bun.file(notesFile).exists())) {
99
- await fs.mkdir(path.dirname(notesFile), { recursive: true })
100
- await Bun.write(notesFile, NOTES_TEMPLATE)
101
- }
102
- }
103
-
104
- // Tail preservation budget (token-budgeted boundary).
105
- // Session-memory compact: minimum guarantees the LLM has enough
106
- // recent-context anchor (avoids the agent-Read-loop failure mode from
107
- // v4 → v5 spec rationale); maximum is a SOFT ceiling on backward
108
- // expansion — i.e. when the natural tail is below the floor we expand
109
- // backward UP TO maxTokens, but if the natural tail already exceeds
110
- // maxTokens we leave it alone. Single-message-granularity cap would
111
- // break tool_use/result pairing.
112
- //
113
- // 20K is the empirical sweet spot — observed compact output is ~20K,
114
- // not the 40K nominal default. The 40K appears in source as fallback,
115
- // but the upstream config likely tunes it lower in production.
116
- const TAIL_MIN_TOKENS = 10_000
117
- const TAIL_MAX_TOKENS = 20_000
118
- const TAIL_MIN_TEXT_BLOCK_MESSAGES = 5
119
-
120
- // Rebuild-time microcompact (see
121
- // docs/superpowers/specs/2026-06-03-rebuild-tail-microcompact-design.md).
122
- //
123
- // After computing the boundary, msgs strictly newer than the boundary
124
- // survive into the rebuild context. Their tool_use parts are kept (so the
125
- // LLM still sees what action was taken), but for tools in this whitelist
126
- // the tool_result content is replaced with a placeholder. Result is either
127
- // large-and-regeneratable (read/bash/grep/glob/webfetch/websearch) or
128
- // essentially a "done" confirmation (edit/write/multiedit). Tools NOT here
129
- // carry state the LLM references later (actor/task/question/skill/memory).
130
- const COMPACTABLE_TOOL_NAMES = new Set<string>([
131
- "read",
132
- "bash",
133
- "grep",
134
- "glob",
135
- "webfetch",
136
- "websearch",
137
- "edit",
138
- "write",
139
- "multiedit",
140
- "apply_patch",
141
- "codesearch",
142
- ])
143
-
144
- function estimateMessageTokens(m: { parts: Array<{ type: string; [k: string]: unknown }> }): number {
145
- // Same estimator used elsewhere in checkpoint.ts (Token.estimate over JSON).
146
- // Sum across all parts of the message.
147
- let sum = 0
148
- for (const p of m.parts) {
149
- // JSON.stringify throws on circular structures. Parser-produced parts are
150
- // plain POJOs, but a plugin-injected part could contain a cycle. Fall back
151
- // to a conservative NON-ZERO estimate so a bad part is never counted as
152
- // "free" — a 0 here would let the tail-boundary algorithm swallow the part
153
- // for nothing and skew the budget. The constant overstates a typical part,
154
- // which is the safe direction (boundary walks back, never forward).
155
- try {
156
- sum += Token.estimate(JSON.stringify(p))
157
- } catch {
158
- sum += 1000
159
- }
160
- }
161
- return sum
162
- }
163
-
164
- function hasTextBlocks(m: { parts: Array<{ type: string }> }): boolean {
165
- return m.parts.some((p) => p.type === "text" || p.type === "reasoning")
166
- }
167
-
168
- /**
169
- * Token-budgeted, role-aware boundary choice for the preserved tail.
170
- *
171
- * Returns the ID of the FIRST message to preserve (boundary message ID;
172
- * everything strictly before this ID is summarized into checkpoint.md and
173
- * discarded from the rebuild context).
174
- *
175
- * Algorithm (token-budgeted boundary):
176
- *
177
- * 1. Start at the last finished assistant index minus 1, take it+successors
178
- * as the candidate tail (preserves spec 2 starting point so reasonable
179
- * tails are unchanged).
180
- * 2. If tail tokens already >= TAIL_MAX_TOKENS: leave boundary as-is and
181
- * return. Do NOT pull boundary forward — message-granularity truncation
182
- * would split tool_use/tool_result pairs (downstream
183
- * adjustBoundaryForApiInvariants would just walk back, net no-op + risk
184
- * of thinking-block breaks). The cap is a SOFT ceiling on backward
185
- * expansion, not a hard upper bound on tail size. If a single
186
- * assistant turn legitimately produces 60K of tool_result, the tail
187
- * will be 60K and that's fine.
188
- * 3. Else if tail tokens < TAIL_MIN_TOKENS or text-block messages < min:
189
- * walk backward (earlier) one message at a time until both minimums
190
- * met OR TAIL_MAX_TOKENS hit OR no more messages.
191
- *
192
- * The downstream adjustBoundaryForApiInvariants call (in
193
- * tryStartCheckpointWriter) handles tool_use/tool_result pairing and
194
- * thinking-block atomicity — this function does NOT need to.
195
- *
196
- * Edge cases:
197
- * - msgs.length === 0: return "" (matches old behavior).
198
- * - No finished assistant: return msgs[0].info.id (degenerate; caller should
199
- * not be invoking trim here, but stay safe).
200
- * - lastAsstIdx === 0: return msgs[0].info.id (degenerate tail).
201
- */
202
- export function computeBoundary(
203
- msgs: ReadonlyArray<{ info: { id: string; role: "user" | "assistant"; finish?: string }; parts: Array<{ type: string; [k: string]: unknown }> }>,
204
- ): string {
205
- if (msgs.length === 0) return ""
206
- const lastAsstIdx = msgs.findLastIndex(
207
- (m) => m.info.role === "assistant" && m.info.finish !== undefined,
208
- )
209
- if (lastAsstIdx <= 0) return msgs[lastAsstIdx >= 0 ? lastAsstIdx : 0].info.id
210
-
211
- // Token estimate per message (computed once).
212
- const tokens = msgs.map((m) => estimateMessageTokens(m))
213
-
214
- // Spec 2 starting point: lastAsstIdx - 1.
215
- let startIdx = lastAsstIdx - 1
216
- let tailSum = 0
217
- let textBlockCount = 0
218
- for (let i = startIdx; i < msgs.length; i++) {
219
- tailSum += tokens[i]
220
- if (hasTextBlocks(msgs[i])) textBlockCount += 1
221
- }
222
-
223
- // Natural tail already >= cap: leave it alone (soft ceiling; do NOT pull
224
- // boundary forward — see jsdoc rationale).
225
- if (tailSum >= TAIL_MAX_TOKENS) {
226
- return msgs[startIdx].info.id
227
- }
228
-
229
- // Tail too small — pull boundary earlier (include more history)
230
- // until both floors met, capped at TAIL_MAX_TOKENS.
231
- while (
232
- startIdx > 0 &&
233
- tailSum < TAIL_MAX_TOKENS &&
234
- (tailSum < TAIL_MIN_TOKENS || textBlockCount < TAIL_MIN_TEXT_BLOCK_MESSAGES)
235
- ) {
236
- startIdx -= 1
237
- tailSum += tokens[startIdx]
238
- if (hasTextBlocks(msgs[startIdx])) textBlockCount += 1
239
- }
240
- return msgs[startIdx].info.id
241
- }
242
-
243
- function renderSectionBudgets(budgets: Record<string, number>): string {
244
- const entries = Object.entries(budgets)
245
- if (entries.length === 0) {
246
- throw new Error("CHECKPOINT_SECTION_BUDGETS is empty — F43 substitution would produce an empty prompt block")
247
- }
248
- const cols = 3
249
- const lines: string[] = ["Section budgets (~tokens):"]
250
- for (let i = 0; i < entries.length; i += cols) {
251
- const row = entries
252
- .slice(i, i + cols)
253
- .map(([k, v]) => `${k}: ${v}`)
254
- .join(" ")
255
- lines.push(` ${row}`)
256
- }
257
- return lines.join("\n")
258
- }
259
-
260
- /**
261
- * Composes the full writer prompt for the checkpoint subagent.
262
- *
263
- * The body wraps PROMPT_CHECKPOINT_WRITER with an ABSOLUTE-PATHS preamble
264
- * that pins CHECKPOINT_PATH/MEMORY_PATH/TASK_MEM_DIR to the current session's
265
- * dirs — without this, the model frequently invents legacy `/data/checkpoints/`
266
- * style paths from training-data lookalikes.
267
- */
268
- function composeWriterPrompt(input: {
269
- checkpointFile: string
270
- memoryFile: string
271
- taskMemDir: string
272
- notesFile: string
273
- rangeDesc: string
274
- progressDiff: string // Spec ② Chain 2: empty string when nothing to reconcile
275
- }): string {
276
- return [
277
- "<system-reminder>",
278
- "You are now operating in checkpoint-writer mode. Ignore the general coding-assistant framing in the system prompt above. The read, write, edit, glob, grep, and task tools are available; do not invoke others.",
279
- "",
280
- "========================================================================",
281
- "ABSOLUTE PATHS — USE THESE VERBATIM. NEVER COMPUTE, INFER, OR MODIFY.",
282
- "========================================================================",
283
- "",
284
- `CHECKPOINT_PATH = ${input.checkpointFile}`,
285
- `MEMORY_PATH = ${input.memoryFile}`,
286
- `TASK_MEM_DIR = ${input.taskMemDir}`,
287
- `NOTES_PATH = ${input.notesFile}`,
288
- "",
289
- "When using the Write tool, the first arg MUST be one of these literal",
290
- "absolute paths (or for task narrative, TASK_MEM_DIR + '/' + task_id +",
291
- "'/progress.md' or '/notes.md'). Do NOT abbreviate. Do NOT change",
292
- "parent directories. Do NOT insert paths from memory of similar projects.",
293
- "If you find yourself typing '/data/checkpoints/' as a parent, STOP — that",
294
- "is the legacy v2 layout and is wrong. The current parent for the",
295
- "checkpoint file is the directory portion of CHECKPOINT_PATH above.",
296
- "========================================================================",
297
- "",
298
- input.progressDiff,
299
- "",
300
- PROMPT_CHECKPOINT_WRITER.replace("{{SECTION_BUDGETS}}", renderSectionBudgets(CHECKPOINT_SECTION_BUDGETS)),
301
- "</system-reminder>",
302
- "",
303
- `Write the next checkpoint for this session.`,
304
- "",
305
- input.rangeDesc,
306
- "",
307
- "Use the `task` tool for ALL task state ops (create / start / progress / done / abandon / approve / rename / block / unblock / batch_create). Use the Write tool for the checkpoint, memory, and task narrative files at the CHECKPOINT_PATH / MEMORY_PATH / TASK_MEM_DIR locations declared above. After all writes and tool calls, stop immediately.",
308
- ].join("\n")
309
- }
310
-
311
- function aggregateWriterCacheMetrics(
312
- sessions: Session.Interface,
313
- sessionID: SessionID,
314
- actorID: string,
315
- ) {
316
- return Effect.gen(function* () {
317
- const msgs = yield* sessions.messages({ sessionID, agentID: "*" })
318
- let totalInput = 0
319
- let cacheRead = 0
320
- let cacheWrite = 0
321
- let assistantCount = 0
322
- for (const m of msgs) {
323
- if (m.info.role !== "assistant") continue
324
- if (m.info.agentID !== actorID) continue
325
- // Count every assistant LLM call in the slice, even ones without
326
- // billing-token data (errors / mid-stream interrupts). Token sums
327
- // skip the no-data rows; the call count includes them so downstream
328
- // consumers can distinguish "low cache hit" from "few calls".
329
- assistantCount += 1
330
- const t = m.info.tokens
331
- if (!t) continue
332
- totalInput += (t.input ?? 0) + (t.cache?.read ?? 0) + (t.cache?.write ?? 0)
333
- cacheRead += t.cache?.read ?? 0
334
- cacheWrite += t.cache?.write ?? 0
335
- }
336
- const billable = totalInput - cacheRead - cacheWrite
337
- const denom = cacheRead + Math.max(billable, 0)
338
- const hitRate = denom > 0 ? cacheRead / denom : 0
339
- return {
340
- total_input_tokens: totalInput,
341
- cache_read_tokens: cacheRead,
342
- cache_write_tokens: cacheWrite,
343
- cache_hit_rate: hitRate,
344
- num_llm_calls: assistantCount,
345
- }
346
- })
347
- }
348
-
349
- // ---------------------------------------------------------------------------
350
- // Service interface
351
- // ---------------------------------------------------------------------------
352
-
353
- export type TryStartCheckpointWriterInput = {
354
- sessionID: SessionID
355
- model: { providerID: string; modelID: string }
356
- promptOps: ActorPromptOps
357
- }
358
-
359
- /**
360
- * Outcome of a tryStartCheckpointWriter call:
361
- * - "started": no writer was running for this session, a fresh one was forked.
362
- * - "queued": a writer is already running. The new request is held in the
363
- * 1-slot pending queue and will fire once the current writer
364
- * settles. If a pending request already exists it's evicted —
365
- * newest wins because its range is a strict superset of the
366
- * older pending range, so the older one would just duplicate
367
- * work. (F40)
368
- * - "skipped": the request was rejected outright — empty session, system-
369
- * spawned subagent, or Actor service unavailable. No writer
370
- * will fire for this request now or later.
371
- */
372
- export type TryStartCheckpointWriterResult = "started" | "queued" | "skipped"
373
-
374
- export interface Interface {
375
- readonly tryStartCheckpointWriter: (
376
- input: TryStartCheckpointWriterInput,
377
- ) => Effect.Effect<TryStartCheckpointWriterResult>
378
-
379
- readonly waitForWriter: (sessionID: SessionID) => Effect.Effect<WriterOutcome | "no-writer">
380
-
381
- /**
382
- * Await all in-flight writers across sessions up to `timeoutMs`. Used by
383
- * the CLI shutdown path so headless `mimo run` invocations don't exit
384
- * while a forked checkpoint writer is still waiting on its LLM round-trip.
385
- * Returns the count of writers that completed vs. still pending when the
386
- * timeout fired.
387
- */
388
- readonly drainWriters: (input?: { timeoutMs?: number }) => Effect.Effect<{
389
- drained: number
390
- timedOut: number
391
- }>
392
-
393
- readonly hasCheckpoint: (sessionID: SessionID) => Effect.Effect<boolean>
394
-
395
- /**
396
- * Returns true when the session has any memory artifacts:
397
- * either a populated `<data>/memory/sessions/<sid>/` directory, or
398
- * any tasks recorded in the task registry. Used by the per-user-message
399
- * recall reminder so it fires whenever there is anything to recall —
400
- * not only when classic v2 checkpoints exist.
401
- */
402
- readonly hasMemoryOrTasks: (sessionID: SessionID) => Effect.Effect<boolean>
403
-
404
- /** Returns the content of the latest checkpoint file, or undefined if none exists. */
405
- readonly loadLatest: (sessionID: SessionID) => Effect.Effect<string | undefined>
406
-
407
- /** Returns the content of the last N checkpoint files, ordered oldest to newest. */
408
- readonly loadCheckpoints: (sessionID: SessionID, count: number) => Effect.Effect<string[]>
409
-
410
- /** Returns a human-readable index overview for injection into rebuild context. */
411
- readonly renderIndex: (sessionID: SessionID) => Effect.Effect<string>
412
-
413
- /**
414
- * Returns the rebuild-time context that should be injected after trim.
415
- * Format:
416
- * <system-reminder>Verify-before-act note...</system-reminder>
417
- * ## Accumulated learnings (chronological)
418
- * ### From checkpoint #1 (<topic>)
419
- * <Learning body>
420
- * ...
421
- * ## Current snapshot (as of checkpoint #N)
422
- * <Snapshot body>
423
- *
424
- * Stale Snapshots from older checkpoints are intentionally dropped. Returns
425
- * an empty string if no checkpoints exist. When checkpoints exist but all
426
- * Learning sections are empty, emits "(no prior learnings)" placeholder;
427
- * when the latest checkpoint has no Snapshot section, emits
428
- * "(latest checkpoint has no Snapshot section)" placeholder — the full
429
- * structure is always produced so the verify-before-act reminder is
430
- * consistently visible.
431
- */
432
- readonly renderRebuildContext: (
433
- sessionID: SessionID,
434
- opts?: { lastMessageInfo?: LastMessageInfo; agentID?: string },
435
- ) => Effect.Effect<string>
436
-
437
- readonly lastBoundary: (sessionID: SessionID) => Effect.Effect<MessageID | undefined>
438
-
439
- readonly isWriterRunning: (sessionID: SessionID) => Effect.Effect<boolean>
440
-
441
- /**
442
- * Insert a synthetic checkpoint-boundary user message (boundary marker +
443
- * index overview + rebuild context + active-actors text) just after the
444
- * given boundary. Inserts nothing and returns false when rebuild context is
445
- * empty. Never deletes DB messages.
446
- */
447
- readonly insertRebuildBoundary: (input: {
448
- sessionID: SessionID
449
- boundary: MessageID
450
- lastMessageInfo?: LastMessageInfo
451
- agentID?: string
452
- agent: string
453
- model: { providerID: string; modelID: string }
454
- boundaryCreatedAt?: number
455
- }) => Effect.Effect<boolean>
456
- }
457
-
458
- export class Service extends Context.Service<Service, Interface>()("@opencode/SessionCheckpoint") {}
459
-
460
- // ---------------------------------------------------------------------------
461
- // Writer state per session
462
- // ---------------------------------------------------------------------------
463
-
464
- export type WriterOutcome = "success" | "failure"
465
-
466
- interface WriterState {
467
- // Holds the AgentOutcome Deferred returned by Actor.spawn so callers can
468
- // await writer settlement (waitForWriter / drainWriters). The public
469
- // WriterOutcome translation happens in waitForWriter.
470
- writing: Deferred.Deferred<AgentOutcome>
471
- // F40: 1-slot pending queue. When set, holds the input for a writer that
472
- // should fire as soon as `writing` settles. Newer requests evict older
473
- // pending values — the newest range is always a strict superset of the
474
- // older one, so older pending checkpoints would only duplicate work.
475
- pending?: TryStartCheckpointWriterInput
476
- }
477
-
478
- // ---------------------------------------------------------------------------
479
- // Layer implementation
480
- // ---------------------------------------------------------------------------
481
-
482
- export const layer: Layer.Layer<
483
- Service,
484
- never,
485
- Session.Service | Bus.Service | Config.Service | Memory.Service | TaskRegistry.Service | ActorRegistry.Service
486
- > = Layer.effect(
487
- Service,
488
- Effect.gen(function* () {
489
- const session = yield* Session.Service
490
- const config = yield* Config.Service
491
- const memory = yield* Memory.Service
492
- const taskRegistry = yield* TaskRegistry.Service
493
- const actorRegistry = yield* ActorRegistry.Service
494
- const bus = yield* Bus.Service
495
- const scope = yield* Scope.Scope
496
-
497
- // Plain Map in the layer closure — same approach as compaction.ts
498
- const writers = new Map<SessionID, WriterState>()
499
-
500
- const tryStartCheckpointWriter: (
501
- input: TryStartCheckpointWriterInput,
502
- ) => Effect.Effect<TryStartCheckpointWriterResult> = Effect.fn("SessionCheckpoint.tryStartCheckpointWriter")(function* (
503
- input: TryStartCheckpointWriterInput,
504
- ) {
505
- // F40: writer1 still running. Evict any prior pending and queue this
506
- // request — newest wins because its range is a strict superset of the
507
- // older pending range, so older pending checkpoints would only
508
- // duplicate the work.
509
- const existing = writers.get(input.sessionID)
510
- if (existing) {
511
- if (existing.pending) {
512
- log.info("writer pending evicted (newer range arrived)", { sessionID: input.sessionID })
513
- } else {
514
- log.info("writer already running, queueing", { sessionID: input.sessionID })
515
- }
516
- existing.pending = input
517
- return "queued" as const
518
- }
519
-
520
- // Defensive: skip if called for a system-spawned session. With Task 27's
521
- // writer-as-subagent migration this becomes mostly impossible, but the
522
- // guard stays so future paths that fold a system-spawn actor into the
523
- // main loop don't accidentally re-enter the writer.
524
- if (yield* actorRegistry.isSystemSpawned(input.sessionID, "main")) {
525
- log.info("tryStartCheckpointWriter skipping system-spawned session")
526
- return "skipped" as const
527
- }
528
-
529
- // Mirror parent runLoop's view (prompt.ts:2036-2040) so the writer's
530
- // ForkContext is byte-equal at the watermark moment. Reading the
531
- // unfiltered session stream would let computeBoundary land on a
532
- // subagent/prior-writer assistant turn and misalign the prefix cache.
533
- const sessionInfo = yield* session.get(input.sessionID)
534
- const msgs = yield* MessageV2.filterCompactedEffect(input.sessionID, {
535
- contextFrom: sessionInfo.contextFrom,
536
- contextWatermark: sessionInfo.contextWatermark,
537
- agentID: "main",
538
- })
539
- if (msgs.length === 0) {
540
- log.info("no messages, skipping checkpoint", { sessionID: input.sessionID })
541
- return "skipped" as const
542
- }
543
-
544
- // Compute boundary for last_checkpoint_message_id bookkeeping. Layer 6
545
- // (Task 16): role-aware adjustment to ensure tool_use/tool_result pairs
546
- // and same-message.id thinking blocks aren't split. OpenCode's ToolPart
547
- // carries both use (input) and result (output) on the SAME message, so
548
- // we project each ToolPart to both a tool_use and a tool_result block —
549
- // pairing is intrinsically satisfied today and the algorithm acts as a
550
- // no-op. Wiring is in place so future tool_result extraction
551
- // (separate user message) will walk the boundary correctly
552
- // without further changes here.
553
- const candidateID = computeBoundary(msgs)
554
- const candidateIdx = msgs.findIndex((m) => m.info.id === candidateID)
555
- const adjustedIdx = adjustBoundaryForApiInvariants(
556
- msgs.map((m) => ({
557
- role: m.info.role,
558
- id: m.info.id,
559
- content: m.parts.flatMap((p) =>
560
- p.type === "tool"
561
- ? [
562
- { type: "tool_use", id: p.callID },
563
- { type: "tool_result", tool_use_id: p.callID },
564
- ]
565
- : [],
566
- ),
567
- })),
568
- Math.max(candidateIdx, 0),
569
- )
570
- const endMessageID = msgs[adjustedIdx]?.info.id ?? candidateID
571
-
572
- // v5 paths: single checkpoint.md per session, single memory.md per
573
- // project (carries across sessions in the same repo), task narrative
574
- // under <sid>/tasks/<id>/. Resolve projectID once HERE — Instance.current
575
- // is ALS-bound and lost once the writer subagent fiber detaches.
576
- const projectID =
577
- (yield* Effect.try({
578
- try: () => Instance.current?.project?.id as ProjectID | undefined,
579
- catch: () => undefined,
580
- }).pipe(Effect.orElseSucceed(() => undefined))) ?? ProjectID.global
581
- const sessMemDir = metaDir(input.sessionID)
582
- const projectMemDir = path.join(Global.Path.data, "memory", "projects", projectID)
583
- const checkpointFile = checkpointPath(input.sessionID)
584
- const memoryFile = memoryPath(projectID)
585
- const taskMemDir = path.join(sessMemDir, "tasks")
586
- const notesFile = notesPath(input.sessionID)
587
-
588
- // Ensure dirs exist before writer fires
589
- yield* Effect.promise(() => fs.mkdir(sessMemDir, { recursive: true }))
590
- yield* Effect.promise(() => fs.mkdir(taskMemDir, { recursive: true }))
591
- yield* Effect.promise(() => fs.mkdir(projectMemDir, { recursive: true }))
592
-
593
- // Migrate legacy lowercase memory.md → MEMORY.md before templating/reading.
594
- yield* Effect.promise(() => migrateProjectMemory(projectID))
595
-
596
- // Bootstrap checkpoint.md, memory.md, and notes.md from templates if missing.
597
- // Self-contained helpers also mkdir parent so they're safe in isolation.
598
- yield* Effect.promise(() => ensureCheckpointTemplate(checkpointFile))
599
- yield* Effect.promise(() => ensureMemoryTemplate(memoryFile))
600
- yield* Effect.promise(() => ensureNotesTemplate(notesFile))
601
-
602
- // v5: single-file checkpoint, check if prior content exists
603
- const checkpointExists = yield* Effect.promise(() => Bun.file(checkpointFile).exists())
604
- const memoryExists = yield* Effect.promise(() => Bun.file(memoryFile).exists())
605
- const rangeDesc = checkpointExists
606
- ? [
607
- `Previous checkpoint: ${checkpointFile}`,
608
- memoryExists ? `Previous memory: ${memoryFile}` : "",
609
- "Read BOTH the prior checkpoint (to dedupe Discovered/Dead-end titles AND to carry forward Live Resources, Execution-context frames, and Session-metadata fields that are still alive) AND the prior memory (project memory) before writing yours.",
610
- ]
611
- .filter((s) => s.length > 0)
612
- .join("\n")
613
- : "This is the first checkpoint of this session. No prior checkpoint exists; MEMORY.md and the task narrative directory likely don't exist yet either."
614
-
615
- const progressDiff = yield* Effect.promise(() => buildProgressDiff(input.sessionID))
616
- const promptText = composeWriterPrompt({ checkpointFile, memoryFile, taskMemDir, notesFile, rangeDesc, progressDiff })
617
-
618
- // v6: spawn writer as subagent — shared sessionID, automatic
619
- // ActorRegistry registration, automatic tool whitelist enforcement
620
- // via permission system. Replaces the legacy session.create + manual
621
- // forkDetach + WriterState tracking that lived here pre-Task-27.
622
- //
623
- // Resolved via spawnRef rather than `yield* Actor.Service` to break the
624
- // (Actor → SessionPrompt → SessionCheckpoint → Actor) layer cycle.
625
- const actor = spawnRef.current
626
- if (!actor) {
627
- log.warn("tryStartCheckpointWriter skipping — Actor service unavailable", { sessionID: input.sessionID })
628
- return "skipped" as const
629
- }
630
-
631
- // Axis B: branch forkContext shape on config.checkpoint.fork.
632
- // - true → preserve existing prefix-cache parent-fork behavior
633
- // (parent agent's system + tools, full slice up to watermark).
634
- // - false → cold-start: writer's own system + tools, delta slice since
635
- // last_checkpoint_message_id (aligned past tool_use/tool_result).
636
- // See spec 2026-06-09-checkpoint-writer-child-session-and-no-fork-fallback-design.md §3.
637
- //
638
- // Default-behavior change at this PR: previously the writer always forked
639
- // the parent's full prefix (effectively fork: true). The default is now
640
- // false (no-fork delta-only). Users on cache-breakpoint providers
641
- // (Anthropic) who want to retain the prefix-cache benefit must set
642
- // `checkpoint.fork: true` in their config. See the spec at
643
- // docs/superpowers/specs/2026-06-09-checkpoint-writer-child-session-and-no-fork-fallback-design.md §4.5.
644
- const cfg = yield* config.get()
645
- const forkMode = cfg.checkpoint?.fork ?? false
646
-
647
- const parentRow = yield* Effect.sync(() =>
648
- Database.use((d) =>
649
- d.select({ last: SessionTable.last_checkpoint_message_id })
650
- .from(SessionTable)
651
- .where(eq(SessionTable.id, input.sessionID))
652
- .get(),
653
- ),
654
- ).pipe(Effect.catch(() => Effect.succeed(undefined as { last: MessageID | null } | undefined)))
655
- const lastCheckpointMessageID = parentRow?.last ?? undefined
656
-
657
- // Hoisted watermark + delta computation: must run BEFORE session.create
658
- // so an empty-delta fork:false call short-circuits to "skipped" without
659
- // creating a child session or invoking actor.spawn. Pre-fix, the
660
- // empty-delta path fell through to spawn → runLoop's
661
- // `isForkAgent && !forkCtx → break` → settle watcher resolved success →
662
- // parent's last_checkpoint_message_id advanced silently (stale checkpoint).
663
- const watermarkIdx = msgs.findIndex((m) => m.info.id === endMessageID)
664
- if (watermarkIdx < 0) {
665
- log.warn("tryStartCheckpointWriter: watermark message not found, skipping", {
666
- sessionID: input.sessionID,
667
- endMessageID,
668
- })
669
- return "skipped" as const
670
- }
671
-
672
- // For fork:false only: precompute the aligned delta and bail if empty.
673
- // fork:true uses msgs.slice(0, watermarkIdx + 1) which is never empty
674
- // given msgs.length > 0 and watermarkIdx >= 0.
675
- const lastIdx = lastCheckpointMessageID
676
- ? msgs.findIndex((m) => m.info.id === lastCheckpointMessageID)
677
- : -1
678
- const rawDeltaStart = lastIdx >= 0 ? lastIdx + 1 : 0
679
- const alignedStart = alignToNonToolResultUser(
680
- msgs.map((m) => ({ info: { role: m.info.role }, parts: m.parts })),
681
- rawDeltaStart,
682
- )
683
- const delta = forkMode ? [] : msgs.slice(alignedStart, watermarkIdx + 1)
684
- if (!forkMode && delta.length === 0) {
685
- // Empty delta under fork:false signals either (a) a degenerate
686
- // session, or (b) a bug elsewhere advanced last_checkpoint_message_id
687
- // past the watermark. Either way, spawning a writer would be a
688
- // silent no-op that would still advance the watermark on settle —
689
- // skip visibly so it's observable in logs.
690
- log.warn("tryStartCheckpointWriter: empty delta under fork:false, skipping", {
691
- sessionID: input.sessionID,
692
- endMessageID,
693
- lastCheckpointMessageID,
694
- })
695
- return "skipped" as const
696
- }
697
-
698
- // Capture parent's view at the watermark for prefix-cache alignment.
699
- // See docs/superpowers/specs/2026-05-26-fork-agent-prefix-cache-design.md
700
- //
701
- // prefixCaptureRef is populated by SessionPrompt.layer to break the
702
- // (ToolRegistry → SessionCheckpoint → ToolRegistry) layer cycle.
703
- const buildPrefix = prefixCaptureRef.current
704
- if (!buildPrefix) {
705
- log.warn("tryStartCheckpointWriter: prefixCaptureRef not set, spawning without forkContext", {
706
- sessionID: input.sessionID,
707
- })
708
- }
709
- const forkCtx: ForkContext | undefined = yield* (buildPrefix
710
- ? Effect.gen(function* () {
711
- const watermarkMsg = msgs[watermarkIdx]
712
- const parentAgentName = (watermarkMsg.info as { agent?: string }).agent
713
- // NOTE: parentAgentName guard is scoped to the forkMode:true branch only —
714
- // fork:false is agent-name-independent (always passes "checkpoint-writer"
715
- // to buildPrefix), so a missing parent agent field must not gate it.
716
-
717
- if (forkMode) {
718
- if (!parentAgentName) {
719
- log.warn(
720
- "tryStartCheckpointWriter: watermark has no agent, fork:true requires parent agent — falling back to no forkContext",
721
- { sessionID: input.sessionID, endMessageID },
722
- )
723
- return undefined as ForkContext | undefined
724
- }
725
- // fork:true — preserve existing prefix-cache parent-fork behavior.
726
- // Build system + tools + inheritedMessages snapshot via capture ref
727
- // using the parent agent's identity and the full slice up to watermark.
728
- // The closure inside SessionPrompt.layer resolves Agent.Info and Provider.Model.
729
- const msgsAtWatermark = msgs.slice(0, watermarkIdx + 1)
730
- const prefix = yield* buildPrefix({
731
- sessionID: input.sessionID,
732
- agentName: parentAgentName,
733
- providerID: input.model.providerID,
734
- modelID: input.model.modelID,
735
- msgs: msgsAtWatermark,
736
- })
737
- return {
738
- system: prefix.system,
739
- tools: prefix.tools,
740
- inheritedMessages: prefix.inheritedMessages,
741
- parentPermission: prefix.parentPermission,
742
- watermarkMsgID: endMessageID as MessageID,
743
- model: {
744
- providerID: input.model.providerID as ProviderID,
745
- modelID: input.model.modelID as ModelID,
746
- },
747
- } satisfies ForkContext
748
- }
749
-
750
- // fork:false — cold-start: use the writer's own system + tools and
751
- // a delta slice since the last checkpoint. capture() resolves the
752
- // checkpoint-writer agent's own definition when agentName is
753
- // "checkpoint-writer", so a single call returns:
754
- // - system + tools = writer's (because agentName === "checkpoint-writer"),
755
- // - inheritedMessages = the delta we pass in, converted to ModelMessage[],
756
- // - parentPermission = writer's own permission (used for tool-availability filter).
757
- // Earlier draft considered two buildPrefix calls (one with msgs:[] for
758
- // system+tools, one with msgs:delta for messages); rejected because
759
- // buildLLMRequestPrefix `Effect.die`s if msgs has no user message.
760
- // Delta is precomputed (and the empty-delta case is short-circuited)
761
- // above, before session.create.
762
- const writerPrefix = yield* buildPrefix({
763
- sessionID: input.sessionID,
764
- agentName: "checkpoint-writer",
765
- providerID: input.model.providerID,
766
- modelID: input.model.modelID,
767
- msgs: delta,
768
- })
769
-
770
- return {
771
- system: writerPrefix.system,
772
- tools: writerPrefix.tools,
773
- inheritedMessages: writerPrefix.inheritedMessages,
774
- parentPermission: writerPrefix.parentPermission,
775
- watermarkMsgID: endMessageID as MessageID,
776
- model: {
777
- providerID: input.model.providerID as ProviderID,
778
- modelID: input.model.modelID as ModelID,
779
- },
780
- } satisfies ForkContext
781
- })
782
- : Effect.succeed(undefined as ForkContext | undefined))
783
-
784
- // Axis A: writer always runs in a fresh child session. This isolates the
785
- // writer's messages and actor registration from the parent so:
786
- // - parent's message table sees zero new rows,
787
- // - parent's `sync.data.actor[parent]` does not include the writer,
788
- // - Ctrl+X subagent cycle / SubagentFooter / DialogSubagent / etc. are
789
- // all naturally clean (they all key on sessionID).
790
- // The writer's checkpoint.md / memory.md / progress paths are absolute and
791
- // computed from input.sessionID (parent) above, so file writes still target
792
- // the parent's artifacts. Settle watcher below also targets parent.
793
- // See spec 2026-06-09-checkpoint-writer-child-session-and-no-fork-fallback-design.md §2.
794
- const writerChildSession = yield* session.create({
795
- parentID: input.sessionID,
796
- title: `checkpoint-writer: ${rangeDesc}`,
797
- })
798
-
799
- // Estimate delta tokens for observability. forkCtx.inheritedMessages is
800
- // ModelMessage[]; an exact count requires the tokenizer, but a rough
801
- // length heuristic is sufficient for the log line.
802
- const deltaApproxBytes = JSON.stringify(forkCtx?.inheritedMessages ?? []).length
803
- log.info("tryStartCheckpointWriter spawning", {
804
- sessionID: input.sessionID,
805
- childSessionID: writerChildSession.id,
806
- mode: forkMode ? "fork" : "no-fork",
807
- deltaApproxBytes,
808
- rangeDesc,
809
- })
810
-
811
- const result = yield* actor.spawn({
812
- mode: "subagent",
813
- sessionID: writerChildSession.id,
814
- // Axis A: writer runs under child session, but its checkpoint.md /
815
- // memory.md / progress paths AND CheckpointContext entries are keyed
816
- // on the PARENT. The splitover plugin reads these via actor.preStop
817
- // and must see parentSessionID to re-derive the right paths — without
818
- // it, checkpointPath(child) returns an empty file and the plugin
819
- // emits a false topic-missing reflection that loops the writer up to
820
- // MAX_PRE_REACT.
821
- parentSessionID: input.sessionID,
822
- agentType: "checkpoint-writer",
823
- description: `checkpoint writer for session ${input.sessionID} covering ${rangeDesc}`,
824
- task: promptText,
825
- context: "full",
826
- tools: ["read", "write", "edit", "apply_patch", "glob", "grep", "task"],
827
- model: {
828
- providerID: input.model.providerID as ProviderID,
829
- modelID: input.model.modelID as ModelID,
830
- },
831
- background: true,
832
- forkContext: forkCtx,
833
- })
834
-
835
- const actorID = result.actorID
836
-
837
- // Capture priorTitles (from checkpoint.md as it stood at the watermark)
838
- // and register the per-actor context entry BEFORE the writer's first
839
- // turn so the splitover plugin's preStop hook can read it. The set
840
- // runs in microseconds; the writer's first LLM round-trip takes
841
- // seconds — no race in practice. See spec §6.1.
842
- const priorTitles = yield* Effect.promise(() => loadPriorDiscoveredTitles(input.sessionID))
843
- CheckpointContext.set(input.sessionID, actorID, {
844
- priorTitles,
845
- expectedRevisions: [],
846
- })
847
-
848
- writers.set(input.sessionID, { writing: result.outcome })
849
-
850
- // Bookkeeping: the parent's last_checkpoint_message_id advances when the
851
- // writer settles. Fork into the layer's scope so the watcher survives
852
- // tryStartCheckpointWriter returning (background: true semantics) but is still tied
853
- // to the layer's lifetime — no orphan fiber on shutdown.
854
- yield* Effect.gen(function* () {
855
- const outcome = yield* Deferred.await(result.outcome)
856
- yield* Effect.sync(() =>
857
- Database.use((d) =>
858
- d.update(SessionTable)
859
- .set({ last_checkpoint_message_id: endMessageID as MessageID })
860
- .where(eq(SessionTable.id, input.sessionID))
861
- .run(),
862
- ),
863
- )
864
-
865
- // F40: capture pending before deleting the slot so a queued writer
866
- // (held while writer1 was running) can fire as a fresh writer.
867
- const pending = writers.get(input.sessionID)?.pending
868
- writers.delete(input.sessionID)
869
-
870
- // F44: aggregate writer slice tokens and emit cache-perf metric so
871
- // prefix-cache reuse is empirically observable. Degrades to zeros if
872
- // aggregation fails (e.g. session messages unavailable post-shutdown).
873
- const stats = yield* aggregateWriterCacheMetrics(session, input.sessionID, result.actorID).pipe(
874
- Effect.catch(() =>
875
- Effect.succeed({
876
- total_input_tokens: 0,
877
- cache_read_tokens: 0,
878
- cache_write_tokens: 0,
879
- cache_hit_rate: 0,
880
- num_llm_calls: 0,
881
- }),
882
- ),
883
- )
884
- yield* bus
885
- .publish(WriterCachePerf, {
886
- sessionID: input.sessionID,
887
- writerActorID: result.actorID,
888
- status: outcome.status === "success" ? ("completed" as const) : ("failed" as const),
889
- ...stats,
890
- })
891
- .pipe(Effect.ignore)
892
-
893
- // F40: drain pending. If a queued request exists, fire a fresh writer
894
- // for it. Errors are swallowed — the queued writer's failure should
895
- // not interrupt the original writer's settlement watcher.
896
- if (pending) {
897
- log.info("draining pending writer", { sessionID: input.sessionID })
898
- yield* tryStartCheckpointWriter(pending).pipe(Effect.ignore)
899
- }
900
- }).pipe(
901
- Effect.ensuring(
902
- Effect.sync(() => CheckpointContext.remove(input.sessionID, actorID)),
903
- ),
904
- Effect.forkIn(scope),
905
- )
906
-
907
- return "started" as const
908
- })
909
-
910
- const waitForWriter = Effect.fn("SessionCheckpoint.waitForWriter")(function* (sessionID: SessionID) {
911
- const state = writers.get(sessionID)
912
- if (!state) return "no-writer" as const
913
-
914
- // v2 writers manage 3 file types and frequently take 60-180s; pad to
915
- // 5min so a long-but-honest writer is not mistaken for a failure by
916
- // the prune retry watcher. AgentOutcome → WriterOutcome translation:
917
- // success → "success", failure / cancelled → "failure".
918
- const outcome = yield* Deferred.await(state.writing).pipe(
919
- Effect.timeout(300_000),
920
- Effect.catch(() => Effect.succeed<AgentOutcome>({ status: "failure", error: "timeout" })),
921
- )
922
- return outcome.status === "success" ? ("success" as const) : ("failure" as const)
923
- })
924
-
925
- const drainWriters = Effect.fn("SessionCheckpoint.drainWriters")(function* (input?: { timeoutMs?: number }) {
926
- const timeoutMs = input?.timeoutMs ?? 120_000
927
- const pending = [...writers.values()]
928
- if (pending.length === 0) return { drained: 0, timedOut: 0 }
929
- log.info("draining checkpoint writers before shutdown", {
930
- count: pending.length,
931
- timeoutMs,
932
- })
933
-
934
- // Deferred.await ignores fiber interruption during shutdown because
935
- // it resolves via Deferred.succeed in the detached writer. We only
936
- // need a collective upper bound so a stuck writer doesn't block exit.
937
- yield* Effect.all(
938
- pending.map((state) => Deferred.await(state.writing)),
939
- { concurrency: "unbounded" },
940
- ).pipe(
941
- Effect.timeout(timeoutMs),
942
- Effect.catch(() => Effect.succeed(undefined)),
943
- )
944
-
945
- // Writers delete themselves from the map on success/failure, so anything
946
- // still present after the timeout is a writer that didn't settle in time.
947
- const timedOut = writers.size
948
- const drained = pending.length - timedOut
949
- if (timedOut > 0) log.warn("drain timed out, writers still pending", { drained, timedOut })
950
- else log.info("drain complete", { drained })
951
- return { drained, timedOut }
952
- })
953
-
954
- const hasCheckpoint = Effect.fn("SessionCheckpoint.hasCheckpoint")(function* (sessionID: SessionID) {
955
- return yield* Effect.promise(() => Bun.file(checkpointPath(sessionID)).exists())
956
- })
957
-
958
- const hasMemoryOrTasks = Effect.fn("SessionCheckpoint.hasMemoryOrTasks")(function* (sessionID: SessionID) {
959
- const memoryRoot = yield* memory.root()
960
- const sessMemDir = path.join(memoryRoot, "sessions", sessionID)
961
- const memEntries = yield* Effect.promise(() =>
962
- fs.readdir(sessMemDir).catch(() => [] as string[]),
963
- )
964
- if (memEntries.length > 0) return true
965
- const tasks = yield* taskRegistry.list({ session_id: sessionID, include_terminal: true })
966
- return tasks.length > 0
967
- })
968
-
969
- const loadLatest = Effect.fn("SessionCheckpoint.loadLatest")(function* (sessionID: SessionID) {
970
- const content = yield* Effect.promise(() =>
971
- Bun.file(checkpointPath(sessionID)).text().catch(() => ""),
972
- )
973
- return content || undefined
974
- })
975
-
976
- const loadCheckpoints = Effect.fn("SessionCheckpoint.loadCheckpoints")(function* (
977
- sessionID: SessionID,
978
- _count: number,
979
- ) {
980
- const content = yield* Effect.promise(() =>
981
- Bun.file(checkpointPath(sessionID)).text().catch(() => ""),
982
- )
983
- return content ? [content] : []
984
- })
985
-
986
- const renderIndex = Effect.fn("SessionCheckpoint.renderIndex")(function* (sessionID: SessionID) {
987
- const snapFile = checkpointPath(sessionID)
988
- const exists = yield* Effect.promise(() => Bun.file(snapFile).exists())
989
- if (!exists) return "No checkpoints yet for this session."
990
-
991
- const content = yield* Effect.promise(() => Bun.file(snapFile).text().catch(() => ""))
992
- const topicMatch = content.match(/^Topic:\s*(.+)$/m)
993
- const topic = topicMatch ? topicMatch[1].trim() : "(unknown)"
994
-
995
- const dir = metaDir(sessionID)
996
- const lines: string[] = []
997
- lines.push("## Checkpoint")
998
- lines.push("")
999
- lines.push(`Directory: ${dir}/`)
1000
- lines.push("")
1001
- lines.push(`Current checkpoint (${topic}): checkpoint.md [shown below]`)
1002
- lines.push("")
1003
- lines.push(`Use read("${snapFile}") to access the full checkpoint.`)
1004
-
1005
- return lines.join("\n")
1006
- })
1007
-
1008
- const renderRebuildContext = Effect.fn("SessionCheckpoint.renderRebuildContext")(function* (
1009
- sessionID: SessionID,
1010
- opts?: { lastMessageInfo?: LastMessageInfo; agentID?: string },
1011
- ) {
1012
- // renderRebuildContext is for the user-facing main agent's context rebuild.
1013
- // Subagent-mode actors (system-spawned writers, model-spawned subagents)
1014
- // share the parent's session but don't have their own checkpoint state to
1015
- // render — return empty so the rebuild path is a no-op for them.
1016
- // Note: agentID === "main" must pass through. After F49+F50 the main
1017
- // agent's lastUser.agentID is "main" (DB row→info reconstruction in
1018
- // message-v2.ts populates info.agentID from agent_id column), and the
1019
- // runLoop calls this with that value. Treating "main" as subagent here
1020
- // would skip rebuild → fall through to F39 compaction → context loss.
1021
- if (opts?.agentID && opts.agentID !== "main") return ""
1022
-
1023
- const inFlight = writers.get(sessionID)
1024
- if (inFlight) {
1025
- log.info("rebuild waiting for in-flight writer", { sessionID })
1026
- yield* Effect.race(
1027
- Deferred.await(inFlight.writing).pipe(Effect.as("done" as const)),
1028
- Effect.sleep("60 seconds").pipe(
1029
- Effect.tap(() => Effect.sync(() => log.warn("writer wait timeout — using on-disk checkpoint", { sessionID }))),
1030
- Effect.as("timeout" as const),
1031
- ),
1032
- ).pipe(Effect.catch(() => Effect.succeed("error" as const)))
1033
- }
1034
-
1035
- const cfg = yield* config.get()
1036
- const caps = cfg.checkpoint?.push_caps ?? {}
1037
- const memoryRoot = yield* memory.root()
1038
-
1039
- const sessMemDir = path.join(memoryRoot, "sessions", sessionID)
1040
-
1041
- // Resolve current project ID once. Used by Section 7 (project memory
1042
- // read) and Section 8 (FTS scope filter). ALS-bound — must be resolved
1043
- // before any deferred work.
1044
- const currentProjectID = yield* Effect.try({
1045
- try: () => Instance.current?.project?.id as ProjectID | undefined,
1046
- catch: () => undefined as ProjectID | undefined,
1047
- }).pipe(Effect.catch(() => Effect.succeed<ProjectID | undefined>(undefined)))
1048
- const projectID = currentProjectID ?? ProjectID.global
1049
-
1050
- // Section data: tasks (SQL), session checkpoint (file), project memory (file).
1051
- const tasks = yield* taskRegistry.list({ session_id: sessionID, include_terminal: true })
1052
-
1053
- const checkpointResult = yield* Effect.promise(() =>
1054
- readBudgetedSectionAware(checkpointPath(sessionID), caps.checkpoint ?? 11_000),
1055
- )
1056
- const checkpointText = checkpointResult?.text ?? ""
1057
-
1058
- yield* Effect.promise(() => migrateProjectMemory(projectID))
1059
- const memoryResult = yield* Effect.promise(() =>
1060
- readBudgetedSectionAware(memoryPath(projectID), caps.memory ?? 10_000),
1061
- )
1062
- const memoryText = memoryResult?.text ?? ""
1063
-
1064
- const notesResult = yield* Effect.promise(() =>
1065
- readBudgeted(notesPath(sessionID), caps.notes ?? 6000),
1066
- )
1067
- const notesText = notesResult?.text ?? ""
1068
-
1069
- const globalResult = yield* Effect.promise(() =>
1070
- readBudgetedSectionAware(globalMemoryPath(), caps.global ?? 6000),
1071
- )
1072
- const globalText = globalResult?.text ?? ""
1073
-
1074
- const actors = yield* actorRegistry.listActive()
1075
-
1076
- // Bail early if absolutely nothing to push: no tasks, no memory content, no live actors.
1077
- if (
1078
- tasks.length === 0 &&
1079
- !checkpointText.trim() &&
1080
- !memoryText.trim() &&
1081
- !globalText.trim() &&
1082
- actors.length === 0
1083
- ) {
1084
- return ""
1085
- }
1086
-
1087
- const lines: string[] = []
1088
-
1089
- // F17: Explicit "already loaded" header. Anchors the active recall
1090
- // protocol's "look for this header" instruction in buildMemoryInstructions.
1091
- lines.push(
1092
- "The following blocks are auto-loaded from your session memory. They are already in your context — do not Read them as whole files. Use Grep for specific facts instead.",
1093
- )
1094
- lines.push("")
1095
-
1096
- // Section 3: tasks ledger (hierarchical with subtasks).
1097
- lines.push("## Tasks ledger")
1098
- if (tasks.length === 0) {
1099
- lines.push("(none)")
1100
- } else {
1101
- const topLevel = tasks.filter((t) => !t.parent_task_id)
1102
- const byParent = new Map<string, typeof tasks>()
1103
- for (const t of tasks) {
1104
- if (!t.parent_task_id) continue
1105
- const bucket = byParent.get(t.parent_task_id) ?? []
1106
- bucket.push(t)
1107
- byParent.set(t.parent_task_id, bucket)
1108
- }
1109
- const statusIcon = (s: string) =>
1110
- ({ open: "🔵", in_progress: "🔄", blocked: "🟡", done: "✅", abandoned: "❌" })[s] ?? s
1111
- const ledgerLines: string[] = []
1112
- for (const t of topLevel) {
1113
- ledgerLines.push(`- ${t.id} ${t.status} — ${t.summary}`)
1114
- const subs = byParent.get(t.id) ?? []
1115
- if (subs.length === 0) continue
1116
- const sublist = subs
1117
- .map((s) => `${statusIcon(s.status)}${s.id}`)
1118
- .join(" / ")
1119
- ledgerLines.push(` Subtasks: ${sublist}`)
1120
- }
1121
- lines.push(truncate(ledgerLines.join("\n"), caps.tasks_ledger ?? 2000))
1122
- }
1123
- lines.push("")
1124
-
1125
- // Section 5: session checkpoint (full body, capped).
1126
- if (checkpointText.trim()) {
1127
- lines.push("## Session checkpoint")
1128
- lines.push(checkpointText.trim())
1129
- lines.push("")
1130
- }
1131
-
1132
- // Section 6: active actors ledger (one line per running actor).
1133
- if (actors.length > 0) {
1134
- lines.push("## Active actors")
1135
- let actorBudget = caps.actor_ledger ?? 500
1136
- for (const a of actors) {
1137
- const line = `- ${a.actorID} — ${a.status}, "${a.description}" (agent=${a.agent})`
1138
- const cost = Token.estimate(line)
1139
- if (actorBudget - cost < 0) break
1140
- lines.push(line)
1141
- actorBudget -= cost
1142
- }
1143
- lines.push("")
1144
- }
1145
-
1146
- // Section 7: project memory (full body, capped).
1147
- if (memoryText.trim()) {
1148
- lines.push("## Project memory")
1149
- lines.push(memoryText.trim())
1150
- lines.push("")
1151
- }
1152
-
1153
- // Section 7.4: global memory (full body, capped). User-level cross-project
1154
- // preferences. Placed after project memory (more actionable) and before
1155
- // session notes (more volatile).
1156
- if (globalText.trim()) {
1157
- lines.push("## Global memory")
1158
- lines.push(globalText.trim())
1159
- lines.push("")
1160
- }
1161
-
1162
- // F14 Section 7.5: session notes (full body, capped). Skip if empty.
1163
- if (notesText.trim()) {
1164
- lines.push("## Session notes")
1165
- lines.push(notesText.trim())
1166
- lines.push("")
1167
- }
1168
-
1169
- // Section 8: memory keys index (paths only, omit already-pushed).
1170
- // SQL-scoped to the current session/project + global so other
1171
- // sessions' files are not leaked. Falls back to skipping the projects
1172
- // scope when the current project is the global/non-git fallback.
1173
- // Reconcile first so files written off-tool (e.g. by the checkpoint
1174
- // writer subagent) are visible in the FTS index here.
1175
- yield* memory.reconcile().pipe(Effect.ignore)
1176
- const pushedPaths = new Set(
1177
- [
1178
- memoryPath(projectID),
1179
- checkpointPath(sessionID),
1180
- globalMemoryPath(),
1181
- ].filter((p) => p.length > 0),
1182
- )
1183
-
1184
- const scopeFilter =
1185
- currentProjectID && currentProjectID !== ProjectID.global
1186
- ? or(
1187
- eq(MemoryFtsTable.scope, "global"),
1188
- and(eq(MemoryFtsTable.scope, "sessions"), eq(MemoryFtsTable.scope_id, sessionID as string)),
1189
- and(eq(MemoryFtsTable.scope, "projects"), eq(MemoryFtsTable.scope_id, currentProjectID)),
1190
- )
1191
- : or(
1192
- eq(MemoryFtsTable.scope, "global"),
1193
- and(eq(MemoryFtsTable.scope, "sessions"), eq(MemoryFtsTable.scope_id, sessionID as string)),
1194
- )
1195
- const scopedPaths = yield* Effect.sync(() =>
1196
- Database.use((db) =>
1197
- db.select({ path: MemoryFtsTable.path }).from(MemoryFtsTable).where(scopeFilter).all(),
1198
- ),
1199
- )
1200
- const keyEntries = scopedPaths
1201
- .map((r) => r.path)
1202
- .filter((p) => !pushedPaths.has(p) && !p.includes(`${path.sep}checkpoint${path.sep}learning-`))
1203
- .map((p) => p.replace(memoryRoot + path.sep, ""))
1204
- if (keyEntries.length > 0) {
1205
- lines.push("## Memory keys index")
1206
- let kBudget = caps.memory_titles ?? 500
1207
- for (const entry of keyEntries) {
1208
- const cost = Token.estimate(entry)
1209
- if (kBudget - cost < 0) break
1210
- lines.push(`- ${entry}`)
1211
- kBudget -= cost
1212
- }
1213
- lines.push("")
1214
- }
1215
-
1216
- // Section 10: explicit seam framing for LLM continuity post-rebuild.
1217
- // Compaction-summary pattern: tells the model
1218
- // that preserved messages below are real history, not pseudo-content,
1219
- // so it resumes mid-loop instead of asking "what would you like me
1220
- // to do".
1221
- lines.push("")
1222
- lines.push(
1223
- "This session is being continued from a previous conversation that hit a checkpoint. The session checkpoint and project memory above cover the earlier portion of the conversation.",
1224
- )
1225
- lines.push("")
1226
- lines.push(
1227
- "Recent messages are preserved verbatim below — the assistant turn (and any tool results) you'll see is real history, not pseudo-content. Continue your task by responding to the most recent state.",
1228
- )
1229
- lines.push("")
1230
- lines.push(
1231
- "Resume directly. Do not acknowledge this memory dump, do not recap, do not preface with \"I'll continue\" or similar. Pick up the last task as if the break never happened.",
1232
- )
1233
-
1234
- // Section 11: tail-aware system reminder. Picks the appropriate nudge
1235
- // based on how the preserved tail ends: tool-calls → continue loop,
1236
- // stop → check task spec before stopping again, tool → process results,
1237
- // user → no addendum needed.
1238
- const info = opts?.lastMessageInfo
1239
- if (info) {
1240
- const reminder = (() => {
1241
- switch (info.role) {
1242
- case "assistant":
1243
- if (info.finish === "tool-calls") return autonomousLoopReminder()
1244
- return stopReminder(undefined)
1245
- case "tool":
1246
- return toolResultContinueReminder()
1247
- case "user":
1248
- return ""
1249
- }
1250
- })()
1251
- if (reminder) {
1252
- lines.push("")
1253
- lines.push(reminder)
1254
- }
1255
- }
1256
-
1257
- return lines.join("\n")
1258
- })
1259
-
1260
- const lastBoundary = Effect.fn("SessionCheckpoint.lastBoundary")(function* (sessionID: SessionID) {
1261
- const row = yield* Effect.sync(() =>
1262
- Database.use((db) =>
1263
- db.select({ last_checkpoint_message_id: SessionTable.last_checkpoint_message_id })
1264
- .from(SessionTable)
1265
- .where(eq(SessionTable.id, sessionID))
1266
- .get(),
1267
- ),
1268
- )
1269
- return row?.last_checkpoint_message_id as MessageID | undefined
1270
- })
1271
-
1272
- const isWriterRunning = Effect.fn("SessionCheckpoint.isWriterRunning")(function* (sessionID: SessionID) {
1273
- return writers.has(sessionID)
1274
- })
1275
-
1276
- const insertRebuildBoundary = Effect.fn("SessionCheckpoint.insertRebuildBoundary")(function* (input: {
1277
- sessionID: SessionID
1278
- boundary: MessageID
1279
- lastMessageInfo?: LastMessageInfo
1280
- agentID?: string
1281
- agent: string
1282
- model: { providerID: string; modelID: string }
1283
- boundaryCreatedAt?: number
1284
- }) {
1285
- const rebuildContext = yield* renderRebuildContext(input.sessionID, {
1286
- lastMessageInfo: input.lastMessageInfo,
1287
- agentID: input.agentID,
1288
- }).pipe(Effect.catch(() => Effect.succeed("")))
1289
- if (!rebuildContext) return false
1290
-
1291
- const indexText = yield* renderIndex(input.sessionID).pipe(Effect.catch(() => Effect.succeed("")))
1292
-
1293
- const syntheticTime = (input.boundaryCreatedAt ?? Date.now()) + 1
1294
- const msg = yield* session.updateMessage({
1295
- id: MessageID.ascending(),
1296
- role: "user" as const,
1297
- model: { providerID: input.model.providerID as ProviderID, modelID: input.model.modelID as ModelID },
1298
- sessionID: input.sessionID,
1299
- agent: input.agent,
1300
- time: { created: syntheticTime },
1301
- })
1302
-
1303
- yield* session.updatePart({
1304
- id: PartID.ascending(),
1305
- messageID: msg.id,
1306
- sessionID: input.sessionID,
1307
- type: "checkpoint",
1308
- checkpointDir: "",
1309
- checkpointNumber: 0,
1310
- coveredUpTo: input.boundary,
1311
- })
1312
-
1313
- if (indexText) {
1314
- yield* session.updatePart({
1315
- id: PartID.ascending(),
1316
- messageID: msg.id,
1317
- sessionID: input.sessionID,
1318
- type: "text",
1319
- synthetic: true,
1320
- text: indexText,
1321
- })
1322
- }
1323
-
1324
- yield* session.updatePart({
1325
- id: PartID.ascending(),
1326
- messageID: msg.id,
1327
- sessionID: input.sessionID,
1328
- type: "text",
1329
- synthetic: true,
1330
- text: rebuildContext,
1331
- })
1332
-
1333
- const actorsText = yield* actorRegistry
1334
- .renderForAgent(input.sessionID)
1335
- .pipe(Effect.catch(() => Effect.succeed("")))
1336
- if (actorsText) {
1337
- yield* session.updatePart({
1338
- id: PartID.ascending(),
1339
- messageID: msg.id,
1340
- sessionID: input.sessionID,
1341
- type: "text",
1342
- synthetic: true,
1343
- text: actorsText,
1344
- })
1345
- }
1346
-
1347
- // Microcompact: messages strictly newer than the boundary will survive
1348
- // into the rebuild context. Clear tool_result content for compactable
1349
- // tools so the first uncached request after rebuild is smaller. tool_use
1350
- // is preserved — LLM still sees what action was taken; result body
1351
- // becomes "[Old tool result content cleared]" via the converter at
1352
- // message-v2.ts (ToolStateCompleted → output).
1353
- // See docs/superpowers/specs/2026-06-03-rebuild-tail-microcompact-design.md.
1354
- //
1355
- // boundaryTime resolution (fail-closed):
1356
- // 1. Prefer explicit input.boundaryCreatedAt (production callers
1357
- // compute it but may pass undefined if the boundary message is no
1358
- // longer in their filterCompactedEffect slice).
1359
- // 2. Else look up input.boundary in allMsgs (full DB, includes
1360
- // pre-marker history).
1361
- // 3. Else SKIP — the previous fallback of 0 would clear EVERY
1362
- // completed compactable tool result in the entire session,
1363
- // corrupting future checkpoint writer input. Log a warning.
1364
- const allMsgs = yield* session.messages({ sessionID: input.sessionID, agentID: "*" })
1365
- const boundaryTime =
1366
- input.boundaryCreatedAt ??
1367
- allMsgs.find((m) => m.info.id === input.boundary)?.info.time.created
1368
- if (boundaryTime === undefined) {
1369
- log.warn("microcompact skipped: no boundary timestamp available", {
1370
- sessionID: input.sessionID,
1371
- boundary: input.boundary,
1372
- })
1373
- return true
1374
- }
1375
- let cleared = 0
1376
- for (const m of allMsgs) {
1377
- if (m.info.id === msg.id) continue
1378
- if (m.info.time.created <= boundaryTime) continue
1379
- for (const part of m.parts) {
1380
- if (part.type !== "tool") continue
1381
- if (!COMPACTABLE_TOOL_NAMES.has(part.tool)) continue
1382
- if (part.state.status !== "completed") continue
1383
- if (part.state.time.compacted) continue
1384
- part.state.time.compacted = Date.now()
1385
- yield* session.updatePart(part)
1386
- cleared += 1
1387
- }
1388
- }
1389
- if (cleared > 0) {
1390
- log.info("rebuild microcompact", { sessionID: input.sessionID, cleared })
1391
- }
1392
-
1393
- return true
1394
- })
1395
-
1396
- return Service.of({
1397
- tryStartCheckpointWriter,
1398
- waitForWriter,
1399
- drainWriters,
1400
- hasCheckpoint,
1401
- hasMemoryOrTasks,
1402
- loadLatest,
1403
- loadCheckpoints,
1404
- renderIndex,
1405
- renderRebuildContext,
1406
- lastBoundary,
1407
- isWriterRunning,
1408
- insertRebuildBoundary,
1409
- })
1410
- }),
1411
- )
1412
-
1413
- // ---------------------------------------------------------------------------
1414
- // Default layer
1415
- // ---------------------------------------------------------------------------
1416
-
1417
- // `defaultLayer` no longer requires `Actor.Service`: SessionCheckpoint reaches
1418
- // the Actor implementation through the late-bound `spawnRef` (see
1419
- // `actor/spawn-ref.ts`). This deliberately breaks the otherwise-unresolvable
1420
- // layer cycle Actor → SessionPrompt → SessionCheckpoint → Actor. The AppLayer
1421
- // constructs `Actor.defaultLayer` separately; its initialiser populates
1422
- // `spawnRef`, which `tryStartCheckpointWriter` reads at call time.
1423
- export const defaultLayer = Layer.suspend(() =>
1424
- layer.pipe(
1425
- Layer.provide(Session.defaultLayer),
1426
- Layer.provide(Bus.layer),
1427
- Layer.provide(Config.defaultLayer),
1428
- Layer.provide(Memory.defaultLayer),
1429
- Layer.provide(TaskRegistry.defaultLayer),
1430
- Layer.provide(ActorRegistry.defaultLayer),
1431
- ),
1432
- )
1433
-
1434
- // ---------------------------------------------------------------------------
1435
- // Convenience wrappers
1436
- // ---------------------------------------------------------------------------
1437
-
1438
- const { runPromise } = makeRuntime(Service, defaultLayer)
1439
-
1440
- export async function hasCheckpoint(input: { sessionID: SessionID }) {
1441
- return runPromise((svc) => svc.hasCheckpoint(input.sessionID))
1442
- }
1443
-
1444
- export async function loadLatest(input: { sessionID: SessionID }) {
1445
- return runPromise((svc) => svc.loadLatest(input.sessionID))
1446
- }
1447
-
1448
- export async function loadCheckpoints(input: { sessionID: SessionID; count: number }) {
1449
- return runPromise((svc) => svc.loadCheckpoints(input.sessionID, input.count))
1450
- }
1451
-
1452
- export async function renderIndex(input: { sessionID: SessionID }) {
1453
- return runPromise((svc) => svc.renderIndex(input.sessionID))
1454
- }
1455
-
1456
- export async function renderRebuildContext(input: {
1457
- sessionID: SessionID
1458
- lastMessageInfo?: LastMessageInfo
1459
- agentID?: string
1460
- }) {
1461
- return runPromise((svc) =>
1462
- svc.renderRebuildContext(input.sessionID, { lastMessageInfo: input.lastMessageInfo, agentID: input.agentID }),
1463
- )
1464
- }
1465
-
1466
- export async function lastBoundary(input: { sessionID: SessionID }) {
1467
- return runPromise((svc) => svc.lastBoundary(input.sessionID))
1468
- }
1469
-
1470
- export async function isWriterRunning(input: { sessionID: SessionID }) {
1471
- return runPromise((svc) => svc.isWriterRunning(input.sessionID))
1472
- }
1473
-
1474
- export * as SessionCheckpoint from "./checkpoint"
1475
-
1476
- // Test-only re-export so test code can call composeWriterPrompt without
1477
- // triggering the full SessionCheckpoint Service stack.
1478
- export { composeWriterPrompt as composeWriterPromptForTest }