@vellumai/assistant 0.8.1 → 0.8.3

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 (630) hide show
  1. package/ARCHITECTURE.md +13 -19
  2. package/Dockerfile +75 -1
  3. package/bun.lock +11 -1
  4. package/docker-entrypoint.sh +17 -0
  5. package/docker-init-apt-root.sh +167 -0
  6. package/docker-kata-apt-env.sh +39 -0
  7. package/docs/plugins.md +88 -47
  8. package/docs/skills.md +9 -7
  9. package/examples/plugins/echo/README.md +27 -27
  10. package/examples/plugins/echo/package.json +3 -0
  11. package/examples/plugins/echo/register.ts +31 -31
  12. package/node_modules/@vellumai/slack-text/src/index.test.ts +114 -14
  13. package/node_modules/@vellumai/slack-text/src/index.ts +82 -18
  14. package/openapi.yaml +642 -5
  15. package/package.json +3 -1
  16. package/scripts/generate-openapi.ts +83 -10
  17. package/scripts/sync-llm-catalog.ts +2 -2
  18. package/scripts/sync-web-search-catalog.ts +47 -25
  19. package/src/__tests__/agent-image-optimize.test.ts +11 -3
  20. package/src/__tests__/agent-loop-exit-reason.test.ts +272 -0
  21. package/src/__tests__/agent-loop-provider-error-recording.test.ts +195 -0
  22. package/src/__tests__/agent-wake-disk-pressure-callsite.test.ts +131 -0
  23. package/src/__tests__/anthropic-provider.test.ts +45 -0
  24. package/src/__tests__/app-builder-tool-scripts.test.ts +9 -3
  25. package/src/__tests__/app-executors.test.ts +220 -4
  26. package/src/__tests__/auto-analysis-end-to-end.test.ts +35 -0
  27. package/src/__tests__/bundled-asset.test.ts +6 -6
  28. package/src/__tests__/channel-availability-routes.test.ts +206 -0
  29. package/src/__tests__/channel-delivery-store.test.ts +289 -1
  30. package/src/__tests__/circuit-breaker-pipeline.test.ts +0 -1
  31. package/src/__tests__/clawhub.test.ts +75 -16
  32. package/src/__tests__/compactor-tail-resolution.test.ts +147 -0
  33. package/src/__tests__/config-get-vision-flag.test.ts +136 -0
  34. package/src/__tests__/config-loader-backfill.test.ts +115 -18
  35. package/src/__tests__/config-schema.test.ts +21 -0
  36. package/src/__tests__/config-set-route.test.ts +80 -0
  37. package/src/__tests__/config-sounds-sync.test.ts +97 -0
  38. package/src/__tests__/config-watcher-skill-reseed.test.ts +453 -0
  39. package/src/__tests__/context-search-conversations-source.test.ts +117 -2
  40. package/src/__tests__/context-search-memory-v2-source.test.ts +0 -1
  41. package/src/__tests__/context-search-workspace-source.test.ts +7 -0
  42. package/src/__tests__/context-token-estimator.test.ts +31 -65
  43. package/src/__tests__/conversation-abort-tool-results.test.ts +4 -1
  44. package/src/__tests__/conversation-agent-loop-inference-profile.test.ts +1 -0
  45. package/src/__tests__/conversation-agent-loop-overflow.test.ts +92 -92
  46. package/src/__tests__/conversation-agent-loop.test.ts +59 -1
  47. package/src/__tests__/conversation-error.test.ts +42 -3
  48. package/src/__tests__/conversation-fork-crud.test.ts +82 -0
  49. package/src/__tests__/conversation-inference-profile-route.test.ts +40 -4
  50. package/src/__tests__/conversation-lifecycle.test.ts +173 -0
  51. package/src/__tests__/conversation-media-retry.test.ts +19 -8
  52. package/src/__tests__/conversation-message-sync-tags.test.ts +97 -0
  53. package/src/__tests__/conversation-pairing.test.ts +54 -0
  54. package/src/__tests__/conversation-process-callsite.test.ts +4 -1
  55. package/src/__tests__/conversation-provider-retry-repair.test.ts +5 -1
  56. package/src/__tests__/conversation-queue.test.ts +4 -1
  57. package/src/__tests__/conversation-runtime-assembly.test.ts +102 -13
  58. package/src/__tests__/conversation-slash-queue.test.ts +59 -1
  59. package/src/__tests__/conversation-slash-unknown.test.ts +4 -1
  60. package/src/__tests__/conversation-surfaces-table-action.test.ts +360 -0
  61. package/src/__tests__/conversation-sync-tags.test.ts +235 -0
  62. package/src/__tests__/conversation-workspace-injection.test.ts +5 -1
  63. package/src/__tests__/conversation-workspace-tool-tracking.test.ts +5 -1
  64. package/src/__tests__/credential-security-invariants.test.ts +3 -2
  65. package/src/__tests__/date-context.test.ts +45 -0
  66. package/src/__tests__/db-slack-external-content-normalization.test.ts +301 -0
  67. package/src/__tests__/delete-managed-skill-tool.test.ts +55 -13
  68. package/src/__tests__/disk-pressure-tools.test.ts +1 -0
  69. package/src/__tests__/dm-backfill.test.ts +121 -10
  70. package/src/__tests__/document-tool-security.test.ts +258 -0
  71. package/src/__tests__/dynamic-skill-workflow-prompt.test.ts +0 -1
  72. package/src/__tests__/edit-propagation.test.ts +33 -0
  73. package/src/__tests__/empty-response-pipeline.test.ts +0 -4
  74. package/src/__tests__/external-plugin-loader.test.ts +151 -55
  75. package/src/__tests__/filing-service.test.ts +140 -0
  76. package/src/__tests__/get-skill-detail-audit.test.ts +0 -4
  77. package/src/__tests__/guardian-action-no-hardcoded-copy.test.ts +0 -1
  78. package/src/__tests__/guardian-dispatch.test.ts +1 -0
  79. package/src/__tests__/handlers-skills-memory-v2-reseed.test.ts +43 -62
  80. package/src/__tests__/heartbeat-service.test.ts +24 -164
  81. package/src/__tests__/helpers/channel-test-adapter.ts +0 -2
  82. package/src/__tests__/helpers/tar-fixtures.ts +39 -0
  83. package/src/__tests__/helpers/wait-for.ts +21 -0
  84. package/src/__tests__/history-repair-pipeline.test.ts +0 -3
  85. package/src/__tests__/history-repair.test.ts +73 -0
  86. package/src/__tests__/host-app-control-proxy.test.ts +507 -10
  87. package/src/__tests__/host-proxy-preactivation.test.ts +200 -13
  88. package/src/__tests__/image-credentials.test.ts +1 -1
  89. package/src/__tests__/inbound-slack-persistence.test.ts +2 -0
  90. package/src/__tests__/inference-no-mode-boot-e2e.test.ts +1 -1
  91. package/src/__tests__/inference-profile-reaper.test.ts +4 -2
  92. package/src/__tests__/inference-profile-session-handler.test.ts +18 -6
  93. package/src/__tests__/inference-profile-session-ipc.test.ts +17 -5
  94. package/src/__tests__/injector-background-turn.test.ts +153 -0
  95. package/src/__tests__/injector-chain.test.ts +15 -8
  96. package/src/__tests__/install-skill-routing.test.ts +155 -37
  97. package/src/__tests__/lifecycle-memory-v2-seed.test.ts +99 -3
  98. package/src/__tests__/list-messages-page-latest.test.ts +55 -0
  99. package/src/__tests__/llm-call-pipeline.test.ts +0 -3
  100. package/src/__tests__/llm-callsite-catalog.test.ts +25 -0
  101. package/src/__tests__/llm-catalog-parity.test.ts +58 -13
  102. package/src/__tests__/llm-request-log-agent-loop-exit-reason.test.ts +116 -0
  103. package/src/__tests__/llm-request-log-error-payload.test.ts +138 -0
  104. package/src/__tests__/llm-request-log-source-clickhouse.test.ts +36 -0
  105. package/src/__tests__/llm-request-log-source-factory.test.ts +29 -53
  106. package/src/__tests__/llm-resolver.test.ts +255 -2
  107. package/src/__tests__/llm-usage-store.test.ts +114 -0
  108. package/src/__tests__/managed-profile-guard.test.ts +41 -29
  109. package/src/__tests__/managed-skill-lifecycle.test.ts +109 -18
  110. package/src/__tests__/managed-store.test.ts +84 -192
  111. package/src/__tests__/media-generate-image.test.ts +1 -1
  112. package/src/__tests__/memory-retrieval-pipeline.test.ts +0 -2
  113. package/src/__tests__/messages-after-tiebreaker.test.ts +122 -0
  114. package/src/__tests__/notification-decision-fallback.test.ts +0 -91
  115. package/src/__tests__/notification-decision-strategy.test.ts +14 -31
  116. package/src/__tests__/notification-deep-link.test.ts +15 -0
  117. package/src/__tests__/notification-guardian-path.test.ts +1 -2
  118. package/src/__tests__/notification-platform-adapter.test.ts +5 -4
  119. package/src/__tests__/notification-telegram-adapter.test.ts +1 -0
  120. package/src/__tests__/notification-vellum-adapter.test.ts +113 -0
  121. package/src/__tests__/oauth-commands-routes.test.ts +168 -16
  122. package/src/__tests__/oauth-provider-profiles.test.ts +9 -0
  123. package/src/__tests__/openai-provider.test.ts +242 -3
  124. package/src/__tests__/openai-responses-cutover-guard.test.ts +17 -9
  125. package/src/__tests__/openrouter-provider-only.test.ts +51 -3
  126. package/src/__tests__/openrouter-token-estimation.test.ts +34 -25
  127. package/src/__tests__/overflow-reduce-pipeline.test.ts +0 -2
  128. package/src/__tests__/persistence-pipeline.test.ts +0 -2
  129. package/src/__tests__/{managed-proxy-context.test.ts → platform-proxy-context.test.ts} +7 -2
  130. package/src/__tests__/platform.test.ts +2 -0
  131. package/src/__tests__/plugin-api-shim.test.ts +125 -0
  132. package/src/__tests__/plugin-bootstrap.test.ts +10 -36
  133. package/src/__tests__/plugin-external-api.test.ts +68 -0
  134. package/src/__tests__/plugin-registry.test.ts +0 -77
  135. package/src/__tests__/plugin-route-contribution.test.ts +0 -1
  136. package/src/__tests__/plugin-skill-contribution.test.ts +0 -2
  137. package/src/__tests__/plugin-tool-contribution.test.ts +16 -15
  138. package/src/__tests__/plugin-types.test.ts +3 -13
  139. package/src/__tests__/process-message-background-slack.test.ts +8 -1
  140. package/src/__tests__/process-message-display-content.test.ts +421 -0
  141. package/src/__tests__/provider-catalog-visibility.test.ts +158 -0
  142. package/src/__tests__/provider-error-scenarios.test.ts +111 -0
  143. package/src/__tests__/{provider-managed-proxy-integration.test.ts → provider-platform-proxy-integration.test.ts} +33 -31
  144. package/src/__tests__/scaffold-managed-skill-tool.test.ts +65 -13
  145. package/src/__tests__/schedule-routes.test.ts +50 -3
  146. package/src/__tests__/schedule-store.test.ts +94 -0
  147. package/src/__tests__/scheduler-reuse-conversation.test.ts +54 -7
  148. package/src/__tests__/schema-transforms.test.ts +20 -0
  149. package/src/__tests__/search-skills-unified.test.ts +0 -5
  150. package/src/__tests__/{secret-routes-managed-proxy.test.ts → secret-routes-platform-proxy.test.ts} +1 -1
  151. package/src/__tests__/server-history-render.test.ts +43 -0
  152. package/src/__tests__/skill-load-feature-flag.test.ts +0 -12
  153. package/src/__tests__/skill-load-tool.test.ts +27 -89
  154. package/src/__tests__/skill-memory.test.ts +23 -3
  155. package/src/__tests__/skills-file-content-endpoint.test.ts +9 -38
  156. package/src/__tests__/skills-files-catalog-fallback.test.ts +0 -3
  157. package/src/__tests__/skills-install-extract.test.ts +49 -38
  158. package/src/__tests__/skills-install-staging.test.ts +159 -0
  159. package/src/__tests__/skills-uninstall.test.ts +9 -41
  160. package/src/__tests__/skills.test.ts +51 -58
  161. package/src/__tests__/slack-channel-config.test.ts +9 -0
  162. package/src/__tests__/subagent-tool-filtering.test.ts +50 -0
  163. package/src/__tests__/system-prompt.test.ts +670 -63
  164. package/src/__tests__/terminal-tools.test.ts +28 -1
  165. package/src/__tests__/thread-backfill.test.ts +557 -27
  166. package/src/__tests__/title-generate-pipeline.test.ts +0 -13
  167. package/src/__tests__/token-estimate-pipeline.test.ts +0 -3
  168. package/src/__tests__/tool-error-pipeline.test.ts +0 -3
  169. package/src/__tests__/tool-execute-pipeline.test.ts +0 -5
  170. package/src/__tests__/tool-executor-lifecycle-events.test.ts +1 -1
  171. package/src/__tests__/tool-executor.test.ts +16 -4
  172. package/src/__tests__/tool-result-truncate-pipeline.test.ts +0 -12
  173. package/src/__tests__/turn-events-store.test.ts +256 -0
  174. package/src/__tests__/twilio-routes.test.ts +4 -0
  175. package/src/__tests__/user-plugin-loader.test.ts +0 -7
  176. package/src/__tests__/voice-session-bridge.test.ts +198 -0
  177. package/src/__tests__/web-search-catalog-parity.test.ts +32 -10
  178. package/src/__tests__/workspace-migration-057-repair-stale-gemini-model-ids.test.ts +115 -3
  179. package/src/__tests__/workspace-migration-072-seed-reply-suggestion-callsite.test.ts +50 -0
  180. package/src/__tests__/workspace-migration-073-repair-recall-callsite-empty-profile.test.ts +153 -0
  181. package/src/__tests__/workspace-migration-085-memory-v2-bm25-b-reembed-disabled-v2-pages.test.ts +220 -0
  182. package/src/__tests__/workspace-migration-086-revert-stale-gemini-mis-rewrites.test.ts +269 -0
  183. package/src/__tests__/workspace-migration-087-memory-router-balanced-profile.test.ts +228 -0
  184. package/src/__tests__/workspace-migration-remove-legacy-skills-index.test.ts +309 -0
  185. package/src/__tests__/workspace-migrations-runner.test.ts +111 -3
  186. package/src/a2a/__tests__/agent-card.test.ts +98 -0
  187. package/src/a2a/__tests__/e2e-a2a-channel.test.ts +597 -0
  188. package/src/a2a/__tests__/protocol-helpers.test.ts +113 -0
  189. package/src/a2a/__tests__/task-store.test.ts +246 -0
  190. package/src/a2a/agent-card.ts +58 -0
  191. package/src/a2a/feature-gate.ts +8 -0
  192. package/src/a2a/protocol-constants.ts +21 -0
  193. package/src/a2a/protocol-errors.ts +50 -0
  194. package/src/a2a/protocol-types.ts +162 -0
  195. package/src/a2a/task-store.ts +168 -0
  196. package/src/acp/resolve-agent.ts +1 -1
  197. package/src/agent/image-optimize.ts +13 -5
  198. package/src/agent/loop.ts +167 -18
  199. package/src/calls/voice-session-bridge.ts +61 -42
  200. package/src/channels/config.ts +9 -0
  201. package/src/channels/types.ts +122 -0
  202. package/src/cli/__tests__/unknown-command.test.ts +24 -0
  203. package/src/cli/commands/__tests__/changelog.test.ts +304 -319
  204. package/src/cli/{__tests__ → commands/__tests__}/notifications.test.ts +201 -28
  205. package/src/cli/commands/__tests__/schedules.test.ts +960 -0
  206. package/src/cli/commands/changelog.ts +106 -42
  207. package/src/cli/commands/conversations.ts +102 -17
  208. package/src/cli/commands/default-action.ts +10 -53
  209. package/src/cli/commands/notifications.ts +388 -346
  210. package/src/cli/commands/plugins.ts +252 -0
  211. package/src/cli/commands/schedules.ts +683 -0
  212. package/src/cli/commands/telemetry.ts +40 -0
  213. package/src/cli/lib/__tests__/cli-colors.test.ts +48 -0
  214. package/src/cli/lib/__tests__/confirm-prompt.test.ts +159 -0
  215. package/src/cli/lib/__tests__/install-from-github.test.ts +355 -0
  216. package/src/cli/lib/__tests__/list-installed-plugins.test.ts +154 -0
  217. package/src/cli/lib/__tests__/search-plugins.test.ts +261 -0
  218. package/src/cli/lib/__tests__/uninstall-plugin.test.ts +124 -0
  219. package/src/cli/lib/__tests__/unknown-command.test.ts +106 -0
  220. package/src/cli/lib/cli-colors.ts +12 -0
  221. package/src/cli/lib/confirm-prompt.ts +79 -0
  222. package/src/cli/lib/install-from-github.ts +303 -0
  223. package/src/cli/lib/list-installed-plugins.ts +137 -0
  224. package/src/cli/lib/search-plugins.ts +163 -0
  225. package/src/cli/lib/uninstall-plugin.ts +82 -0
  226. package/src/cli/lib/unknown-command.ts +111 -0
  227. package/src/cli/program.ts +52 -2
  228. package/src/config/assistant-feature-flags.ts +24 -54
  229. package/src/config/bundled-skills/app-builder/SKILL.md +140 -22
  230. package/src/config/bundled-skills/app-builder/TOOLS.json +7 -0
  231. package/src/config/bundled-skills/computer-use/TOOLS.json +15 -52
  232. package/src/config/bundled-skills/document/SKILL.md +23 -3
  233. package/src/config/bundled-skills/document/TOOLS.json +53 -0
  234. package/src/config/bundled-skills/document/tools/document-delete.ts +12 -0
  235. package/src/config/bundled-skills/document/tools/document-list.ts +12 -0
  236. package/src/config/bundled-skills/document/tools/document-read.ts +12 -0
  237. package/src/config/bundled-skills/phone-calls/SKILL.md +1 -1
  238. package/src/config/bundled-skills/skill-management/SKILL.md +2 -2
  239. package/src/config/bundled-skills/skill-management/TOOLS.json +7 -7
  240. package/src/config/bundled-tool-registry.ts +6 -0
  241. package/src/config/call-site-defaults.ts +105 -0
  242. package/src/config/feature-flag-registry.json +41 -9
  243. package/src/config/llm-resolver.ts +52 -1
  244. package/src/config/loader.ts +64 -38
  245. package/src/config/schema.ts +9 -10
  246. package/src/config/schemas/__tests__/llm-request-logs.test.ts +36 -0
  247. package/src/config/schemas/__tests__/memory-v2.test.ts +3 -3
  248. package/src/config/schemas/channels.ts +17 -0
  249. package/src/config/schemas/compaction.ts +28 -0
  250. package/src/config/schemas/conversations.ts +10 -0
  251. package/src/config/schemas/heartbeat.ts +23 -0
  252. package/src/config/schemas/llm-request-logs.ts +31 -7
  253. package/src/config/schemas/llm.ts +1 -0
  254. package/src/config/schemas/memory-retrieval.ts +18 -0
  255. package/src/config/schemas/memory-retrospective.ts +1 -1
  256. package/src/config/schemas/memory-v2.ts +4 -4
  257. package/src/config/schemas/memory.ts +3 -1
  258. package/src/config/schemas/tools.ts +14 -0
  259. package/src/config/seed-inference-profiles.ts +99 -29
  260. package/src/config/skills.ts +3 -96
  261. package/src/context/compactor.ts +1107 -0
  262. package/src/context/token-estimator.ts +34 -36
  263. package/src/context/window-manager.ts +197 -1520
  264. package/src/credential-execution/managed-catalog.ts +37 -0
  265. package/src/credential-health/credential-health-service.ts +280 -19
  266. package/src/daemon/__tests__/conversation-lifecycle-auto-analyze.test.ts +33 -18
  267. package/src/daemon/__tests__/conversation-tool-setup-exclude.test.ts +138 -0
  268. package/src/daemon/__tests__/conversation-tool-setup.test.ts +74 -0
  269. package/src/daemon/approval-generators.ts +8 -6
  270. package/src/daemon/config-watcher.ts +94 -31
  271. package/src/daemon/conversation-agent-loop-handlers.ts +78 -0
  272. package/src/daemon/conversation-agent-loop.ts +198 -11
  273. package/src/daemon/conversation-error.ts +171 -37
  274. package/src/daemon/conversation-lifecycle.ts +53 -40
  275. package/src/daemon/conversation-messaging.ts +25 -6
  276. package/src/daemon/conversation-process.ts +49 -12
  277. package/src/daemon/conversation-runtime-assembly.ts +25 -1
  278. package/src/daemon/conversation-slash.ts +12 -5
  279. package/src/daemon/conversation-store.ts +11 -4
  280. package/src/daemon/conversation-tool-setup.ts +39 -7
  281. package/src/daemon/conversation.ts +33 -8
  282. package/src/daemon/date-context.ts +40 -0
  283. package/src/daemon/external-plugins-bootstrap.ts +217 -181
  284. package/src/daemon/first-greeting.ts +22 -2
  285. package/src/daemon/guardian-action-generators.ts +1 -125
  286. package/src/daemon/handlers/__tests__/config-a2a-complete.test.ts +248 -0
  287. package/src/daemon/handlers/__tests__/config-a2a-invite.test.ts +154 -0
  288. package/src/daemon/handlers/__tests__/config-a2a-redeem.test.ts +133 -0
  289. package/src/daemon/handlers/__tests__/config-a2a.test.ts +95 -0
  290. package/src/daemon/handlers/config-a2a.ts +289 -0
  291. package/src/daemon/handlers/config-model.ts +6 -5
  292. package/src/daemon/handlers/config-slack-channel.ts +15 -3
  293. package/src/daemon/handlers/conversations.ts +1 -0
  294. package/src/daemon/handlers/shared.ts +14 -5
  295. package/src/daemon/handlers/skills.ts +111 -108
  296. package/src/daemon/history-repair.ts +28 -1
  297. package/src/daemon/host-app-control-proxy.ts +153 -27
  298. package/src/daemon/host-proxy-preactivation.ts +85 -18
  299. package/src/daemon/lifecycle.ts +89 -91
  300. package/src/daemon/meet-host-supervisor.ts +5 -4
  301. package/src/daemon/memory-v2-startup.ts +85 -0
  302. package/src/daemon/message-protocol.ts +1 -0
  303. package/src/daemon/message-types/conversations.ts +25 -0
  304. package/src/daemon/message-types/messages.ts +61 -0
  305. package/src/daemon/message-types/notifications.ts +21 -0
  306. package/src/daemon/message-types/subagents.ts +1 -0
  307. package/src/daemon/message-types/sync.ts +1 -0
  308. package/src/daemon/pkb-reminder-builder.test.ts +11 -54
  309. package/src/daemon/pkb-reminder-builder.ts +5 -20
  310. package/src/daemon/plugin-source-watcher.ts +146 -0
  311. package/src/daemon/process-message.ts +24 -3
  312. package/src/daemon/server.ts +11 -2
  313. package/src/daemon/skill-memory-refresh.ts +33 -0
  314. package/src/daemon/wake-target-adapter.ts +2 -0
  315. package/src/documents/document-store.ts +221 -3
  316. package/src/embedded/plugin-api.ts +40 -0
  317. package/src/export/__tests__/transcript-formatter.test.ts +121 -0
  318. package/src/export/transcript-formatter.ts +54 -20
  319. package/src/filing/filing-service.ts +39 -0
  320. package/src/heartbeat/__tests__/heartbeat-service.test.ts +135 -6
  321. package/src/heartbeat/heartbeat-run-store.ts +2 -1
  322. package/src/heartbeat/heartbeat-service.ts +73 -189
  323. package/src/home/__tests__/feed-types.test.ts +80 -0
  324. package/src/home/feed-types.ts +36 -2
  325. package/src/home/post-connect-feed.ts +1 -0
  326. package/src/index.ts +18 -1
  327. package/src/ipc/cli-client.ts +147 -45
  328. package/src/live-voice/__tests__/live-voice-stt.test.ts +57 -0
  329. package/src/mcp/client.ts +20 -4
  330. package/src/media/image-credentials.ts +3 -3
  331. package/src/memory/__tests__/bookmark-crud.test.ts +33 -27
  332. package/src/memory/__tests__/conversation-queries.test.ts +483 -0
  333. package/src/memory/__tests__/jobs-worker-v2-graph-trigger-embed.test.ts +113 -0
  334. package/src/memory/__tests__/memory-retrospective-enqueue.test.ts +2 -50
  335. package/src/memory/__tests__/memory-retrospective-job.test.ts +87 -4
  336. package/src/memory/__tests__/memory-retrospective-startup-cleanup.test.ts +119 -14
  337. package/src/memory/__tests__/message-content.test.ts +35 -0
  338. package/src/memory/bookmark-crud.ts +42 -10
  339. package/src/memory/context-search/sources/conversations.ts +62 -2
  340. package/src/memory/context-search/sources/workspace.ts +4 -0
  341. package/src/memory/conversation-crud.ts +63 -19
  342. package/src/memory/conversation-queries.ts +197 -11
  343. package/src/memory/conversation-title-service.ts +26 -4
  344. package/src/memory/db-init.ts +12 -0
  345. package/src/memory/delivery-crud.ts +152 -5
  346. package/src/memory/embedding-backend.ts +4 -4
  347. package/src/memory/external-conversation-store.ts +66 -5
  348. package/src/memory/graph/__tests__/conversation-graph-memory-v2-routing.test.ts +150 -12
  349. package/src/memory/graph/conversation-graph-memory.ts +49 -21
  350. package/src/memory/graph/tools.ts +9 -40
  351. package/src/memory/indexer.ts +34 -29
  352. package/src/memory/invite-store.ts +53 -0
  353. package/src/memory/jobs/__tests__/embed-concept-page.test.ts +73 -0
  354. package/src/memory/jobs/embed-concept-page.ts +20 -11
  355. package/src/memory/jobs-worker.ts +6 -1
  356. package/src/memory/llm-request-log-source-clickhouse.ts +24 -12
  357. package/src/memory/llm-request-log-source.ts +19 -52
  358. package/src/memory/llm-request-log-store.ts +92 -1
  359. package/src/memory/llm-usage-store.ts +125 -5
  360. package/src/memory/memory-retrospective-enqueue.ts +1 -20
  361. package/src/memory/memory-retrospective-job.ts +33 -6
  362. package/src/memory/memory-retrospective-startup-cleanup.ts +72 -5
  363. package/src/memory/message-content.ts +1 -1
  364. package/src/memory/migrations/109-external-conversation-bindings.ts +15 -4
  365. package/src/memory/migrations/229-delete-private-conversations.test.ts +38 -1
  366. package/src/memory/migrations/229-delete-private-conversations.ts +7 -0
  367. package/src/memory/migrations/247-external-conversation-binding-thread-id.ts +78 -0
  368. package/src/memory/migrations/248-create-onboarding-events.ts +21 -0
  369. package/src/memory/migrations/249-normalize-slack-external-content.ts +240 -0
  370. package/src/memory/migrations/250-provider-connection-base-url-and-models.ts +28 -0
  371. package/src/memory/migrations/251-a2a-tasks.ts +49 -0
  372. package/src/memory/migrations/252-llm-request-log-agent-loop-exit-reason.ts +32 -0
  373. package/src/memory/migrations/index.ts +9 -0
  374. package/src/memory/migrations/registry.ts +16 -0
  375. package/src/memory/onboarding-events-store.ts +106 -0
  376. package/src/memory/schema/a2a.ts +15 -0
  377. package/src/memory/schema/bookmarks.ts +0 -2
  378. package/src/memory/schema/calls.ts +1 -0
  379. package/src/memory/schema/index.ts +1 -0
  380. package/src/memory/schema/inference.ts +3 -3
  381. package/src/memory/schema/infrastructure.ts +13 -0
  382. package/src/memory/turn-events-store.ts +127 -2
  383. package/src/memory/v2/__tests__/activation-store.test.ts +25 -23
  384. package/src/memory/v2/__tests__/activation.test.ts +0 -8
  385. package/src/memory/v2/__tests__/cli-command-store.test.ts +404 -0
  386. package/src/memory/v2/__tests__/frontmatter-sweep.test.ts +25 -4
  387. package/src/memory/v2/__tests__/injection.test.ts +288 -11
  388. package/src/memory/v2/__tests__/migration.test.ts +87 -0
  389. package/src/memory/v2/__tests__/page-index.test.ts +83 -0
  390. package/src/memory/v2/__tests__/prompts-router.test.ts +58 -6
  391. package/src/memory/v2/__tests__/qdrant.test.ts +66 -3
  392. package/src/memory/v2/__tests__/router.test.ts +15 -0
  393. package/src/memory/v2/__tests__/skill-store.test.ts +387 -8
  394. package/src/memory/v2/__tests__/static-context.test.ts +12 -1
  395. package/src/memory/v2/activation-store.ts +14 -16
  396. package/src/memory/v2/cli-command-content.ts +19 -0
  397. package/src/memory/v2/cli-command-store.ts +304 -0
  398. package/src/memory/v2/frontmatter-sweep.ts +7 -1
  399. package/src/memory/v2/injection.ts +81 -26
  400. package/src/memory/v2/migration.ts +49 -19
  401. package/src/memory/v2/page-index.ts +63 -8
  402. package/src/memory/v2/prompts/router.ts +11 -8
  403. package/src/memory/v2/prompts/sweep.ts +2 -2
  404. package/src/memory/v2/qdrant.ts +135 -7
  405. package/src/memory/v2/router.ts +9 -8
  406. package/src/memory/v2/skill-store.ts +120 -35
  407. package/src/memory/v2/static-context.ts +4 -4
  408. package/src/memory/v2/types.ts +23 -0
  409. package/src/messaging/providers/a2a/__tests__/deliver.test.ts +274 -0
  410. package/src/messaging/providers/a2a/deliver.ts +156 -0
  411. package/src/messaging/providers/gmail/client.ts +9 -2
  412. package/src/messaging/providers/index.ts +11 -2
  413. package/src/messaging/providers/slack/__tests__/adapter-token-routing.test.ts +45 -5
  414. package/src/messaging/providers/slack/__tests__/download.test.ts +231 -0
  415. package/src/messaging/providers/slack/adapter.ts +43 -5
  416. package/src/messaging/providers/slack/client.ts +27 -0
  417. package/src/messaging/providers/slack/deep-link.ts +65 -0
  418. package/src/messaging/providers/slack/download.ts +104 -0
  419. package/src/messaging/providers/slack/message-metadata.test.ts +32 -0
  420. package/src/messaging/providers/slack/message-metadata.ts +27 -0
  421. package/src/messaging/providers/slack/render-transcript.test.ts +134 -0
  422. package/src/messaging/providers/slack/render-transcript.ts +69 -5
  423. package/src/messaging/providers/slack/types.ts +20 -1
  424. package/src/notifications/__tests__/broadcaster.test.ts +203 -0
  425. package/src/notifications/__tests__/decision-engine.test.ts +283 -0
  426. package/src/notifications/__tests__/deterministic-checks.test.ts +286 -0
  427. package/src/notifications/__tests__/emit-signal-home-feed.test.ts +1 -0
  428. package/src/notifications/__tests__/home-feed-side-effect.test.ts +430 -7
  429. package/src/notifications/adapters/macos.ts +12 -2
  430. package/src/notifications/broadcaster.ts +29 -4
  431. package/src/notifications/conversation-pairing.ts +2 -1
  432. package/src/notifications/copy-composer.ts +17 -64
  433. package/src/notifications/decision-engine.ts +113 -45
  434. package/src/notifications/deterministic-checks.ts +96 -0
  435. package/src/notifications/emit-signal.ts +21 -1
  436. package/src/notifications/home-feed-side-effect.ts +138 -5
  437. package/src/notifications/signal.ts +3 -5
  438. package/src/notifications/types.ts +8 -0
  439. package/src/oauth/connection-resolver.ts +8 -4
  440. package/src/oauth/platform-connection.test.ts +43 -3
  441. package/src/oauth/platform-connection.ts +19 -6
  442. package/src/oauth/seed-providers.ts +10 -1
  443. package/src/permissions/checker.ts +2 -0
  444. package/src/permissions/ipc-risk-types.ts +1 -0
  445. package/src/permissions/question-prompter.test.ts +416 -0
  446. package/src/permissions/question-prompter.ts +294 -0
  447. package/src/platform/client.test.ts +1 -1
  448. package/src/platform/client.ts +1 -1
  449. package/src/plugin-api/constants.ts +26 -0
  450. package/src/plugin-api/index.ts +34 -1
  451. package/src/plugin-api/types.ts +104 -22
  452. package/src/plugins/defaults/circuit-breaker.ts +0 -5
  453. package/src/plugins/defaults/compaction.ts +0 -4
  454. package/src/plugins/defaults/empty-response.ts +0 -2
  455. package/src/plugins/defaults/history-repair.ts +0 -2
  456. package/src/plugins/defaults/injectors.ts +74 -22
  457. package/src/plugins/defaults/llm-call.ts +0 -2
  458. package/src/plugins/defaults/memory-retrieval.ts +0 -1
  459. package/src/plugins/defaults/overflow-reduce.ts +0 -1
  460. package/src/plugins/defaults/persistence.ts +0 -2
  461. package/src/plugins/defaults/title-generate.ts +0 -5
  462. package/src/plugins/defaults/token-estimate.ts +0 -2
  463. package/src/plugins/defaults/tool-error.ts +0 -7
  464. package/src/plugins/defaults/tool-execute.ts +0 -2
  465. package/src/plugins/defaults/tool-result-truncate.ts +0 -4
  466. package/src/plugins/ensure-plugin-api-shim.ts +96 -0
  467. package/src/plugins/external-api.ts +104 -0
  468. package/src/plugins/external-plugin-loader.ts +187 -42
  469. package/src/plugins/feature-gate.ts +22 -0
  470. package/src/plugins/pipeline.ts +37 -0
  471. package/src/plugins/registry.ts +48 -80
  472. package/src/plugins/types.ts +40 -26
  473. package/src/plugins/user-loader.ts +21 -2
  474. package/src/proactive-artifact/aux-message-injector.ts +11 -0
  475. package/src/proactive-artifact/job.test.ts +37 -5
  476. package/src/prompts/__tests__/system-prompt.test.ts +10 -43
  477. package/src/prompts/__tests__/task-progress-hint-section.test.ts +95 -0
  478. package/src/prompts/normalize-onboarding.ts +27 -0
  479. package/src/prompts/sections.ts +302 -0
  480. package/src/prompts/system-prompt.ts +63 -174
  481. package/src/prompts/templates/BOOTSTRAP.md +17 -1
  482. package/src/prompts/templates/system-sections.ts +164 -0
  483. package/src/providers/__tests__/inference.test.ts +24 -7
  484. package/src/providers/anthropic/client.ts +28 -28
  485. package/src/providers/call-site-routing.ts +24 -6
  486. package/src/providers/connection-resolution.ts +68 -11
  487. package/src/providers/inference/__tests__/adapter-factory-openai-compatible.test.ts +74 -0
  488. package/src/providers/inference/__tests__/connections-openai-compatible.test.ts +175 -0
  489. package/src/providers/inference/__tests__/connections-status-label.test.ts +15 -0
  490. package/src/providers/inference/adapter-factory.ts +32 -6
  491. package/src/providers/inference/auth.ts +12 -0
  492. package/src/providers/inference/backfill.ts +14 -1
  493. package/src/providers/inference/connections.ts +159 -34
  494. package/src/providers/inference/resolve-auth.ts +14 -4
  495. package/src/providers/model-catalog.ts +249 -12
  496. package/src/providers/model-intents.ts +3 -3
  497. package/src/providers/openai/__tests__/chat-completions-provider-reasoning.test.ts +235 -0
  498. package/src/providers/openai/chat-completions-provider.ts +169 -8
  499. package/src/providers/openrouter/client.ts +49 -4
  500. package/src/providers/{managed-proxy → platform-proxy}/constants.ts +4 -2
  501. package/src/providers/{managed-proxy → platform-proxy}/context.ts +3 -3
  502. package/src/providers/provider-availability.ts +17 -2
  503. package/src/providers/provider-catalog-visibility.ts +38 -0
  504. package/src/providers/provider-send-message.ts +27 -12
  505. package/src/providers/registry.ts +52 -15
  506. package/src/providers/retry.ts +47 -1
  507. package/src/runtime/__tests__/agent-wake.test.ts +152 -0
  508. package/src/runtime/agent-wake.ts +103 -15
  509. package/src/runtime/auth/route-policy.ts +21 -1
  510. package/src/runtime/btw-sidechain.ts +2 -0
  511. package/src/runtime/http-server.ts +7 -16
  512. package/src/runtime/http-types.ts +19 -47
  513. package/src/runtime/migrations/origin-mode.ts +1 -1
  514. package/src/runtime/pending-interactions.ts +1 -0
  515. package/src/runtime/routes/__tests__/bookmark-routes.test.ts +17 -0
  516. package/src/runtime/routes/__tests__/consolidation-routes.test.ts +258 -0
  517. package/src/runtime/routes/__tests__/conversation-management-routes.test.ts +5 -1
  518. package/src/runtime/routes/__tests__/conversation-query-routes.test.ts +172 -23
  519. package/src/runtime/routes/__tests__/inference-provider-connection-routes.test.ts +275 -44
  520. package/src/runtime/routes/__tests__/llm-call-sites-routes.test.ts +12 -0
  521. package/src/runtime/routes/__tests__/question-routes.test.ts +395 -0
  522. package/src/runtime/routes/__tests__/tts-routes.test.ts +64 -1
  523. package/src/runtime/routes/acp-routes-list.test.ts +143 -0
  524. package/src/runtime/routes/acp-routes.ts +5 -3
  525. package/src/runtime/routes/auth-routes.ts +1 -1
  526. package/src/runtime/routes/bookmark-routes.ts +5 -3
  527. package/src/runtime/routes/btw-routes.ts +5 -1
  528. package/src/runtime/routes/channel-availability-routes.ts +126 -0
  529. package/src/runtime/routes/consolidation-routes.ts +100 -0
  530. package/src/runtime/routes/conversation-cli-routes.ts +44 -3
  531. package/src/runtime/routes/conversation-list-routes.ts +3 -20
  532. package/src/runtime/routes/conversation-management-routes.ts +17 -42
  533. package/src/runtime/routes/conversation-query-routes.ts +99 -35
  534. package/src/runtime/routes/conversation-routes.ts +97 -11
  535. package/src/runtime/routes/documents-routes.ts +25 -86
  536. package/src/runtime/routes/group-routes.ts +5 -0
  537. package/src/runtime/routes/inbound-conversation.ts +28 -8
  538. package/src/runtime/routes/inbound-message-handler.ts +236 -41
  539. package/src/runtime/routes/inbound-stages/background-dispatch.test.ts +111 -0
  540. package/src/runtime/routes/inbound-stages/background-dispatch.ts +32 -1
  541. package/src/runtime/routes/inbound-stages/edit-intercept.ts +17 -4
  542. package/src/runtime/routes/index.ts +8 -0
  543. package/src/runtime/routes/inference-profile-session-handler.ts +17 -44
  544. package/src/runtime/routes/inference-profile-session-reaper.ts +7 -21
  545. package/src/runtime/routes/inference-provider-connection-routes.ts +199 -22
  546. package/src/runtime/routes/integrations/a2a.ts +235 -0
  547. package/src/runtime/routes/integrations/slack/share.ts +4 -52
  548. package/src/runtime/routes/integrations/slack/token.ts +43 -0
  549. package/src/runtime/routes/integrations/twilio.ts +6 -13
  550. package/src/runtime/routes/llm-call-sites-routes.ts +11 -1
  551. package/src/runtime/routes/notification-routes.ts +1 -1
  552. package/src/runtime/routes/oauth-commands-routes.ts +105 -15
  553. package/src/runtime/routes/oauth-lifecycle-routes.ts +43 -0
  554. package/src/runtime/routes/question-routes.ts +259 -0
  555. package/src/runtime/routes/rename-conversation-routes.ts +2 -33
  556. package/src/runtime/routes/schedule-routes.ts +4 -7
  557. package/src/runtime/routes/subagents-routes.ts +98 -18
  558. package/src/runtime/routes/telemetry-routes.ts +27 -0
  559. package/src/runtime/routes/tts-routes.ts +27 -2
  560. package/src/runtime/routes/workspace-routes.test.ts +43 -0
  561. package/src/runtime/routes/workspace-routes.ts +28 -0
  562. package/src/runtime/services/conversation-serializer.ts +39 -7
  563. package/src/runtime/sync/resource-sync-events.ts +93 -1
  564. package/src/schedule/schedule-store.ts +27 -2
  565. package/src/schedule/scheduler.ts +9 -1
  566. package/src/security/__tests__/untrusted-content.test.ts +86 -0
  567. package/src/security/untrusted-content.ts +93 -8
  568. package/src/skills/catalog-files.ts +1 -1
  569. package/src/skills/catalog-install.ts +233 -116
  570. package/src/skills/clawhub.ts +70 -13
  571. package/src/skills/managed-store.ts +4 -119
  572. package/src/skills/skillssh-registry.ts +27 -48
  573. package/src/subagent/manager.ts +17 -7
  574. package/src/telemetry/types.ts +113 -1
  575. package/src/telemetry/usage-telemetry-reporter.test.ts +312 -5
  576. package/src/telemetry/usage-telemetry-reporter.ts +113 -7
  577. package/src/tools/apps/executors.ts +58 -7
  578. package/src/tools/ask-question/ask-question-tool.test.ts +509 -0
  579. package/src/tools/ask-question/ask-question-tool.ts +304 -0
  580. package/src/tools/browser/browser-execution.ts +15 -11
  581. package/src/tools/computer-use/definitions.ts +3 -3
  582. package/src/tools/credentials/vault.ts +1 -1
  583. package/src/tools/document/document-tool.ts +124 -1
  584. package/src/tools/filesystem/edit.ts +1 -1
  585. package/src/tools/filesystem/list.ts +1 -1
  586. package/src/tools/filesystem/read.ts +1 -1
  587. package/src/tools/filesystem/write.ts +5 -2
  588. package/src/tools/host-filesystem/transfer.ts +1 -1
  589. package/src/tools/host-terminal/host-shell.ts +1 -1
  590. package/src/tools/memory/register.ts +1 -9
  591. package/src/tools/permission-checker.ts +1 -1
  592. package/src/tools/registry.ts +17 -7
  593. package/src/tools/schedule/create.ts +2 -2
  594. package/src/tools/schema-transforms.ts +7 -2
  595. package/src/tools/side-effects.ts +1 -0
  596. package/src/tools/skills/delete-managed.ts +4 -4
  597. package/src/tools/skills/execute.ts +1 -1
  598. package/src/tools/skills/scaffold-managed.ts +3 -2
  599. package/src/tools/subagent/notify-parent.ts +1 -1
  600. package/src/tools/system/request-permission.ts +2 -2
  601. package/src/tools/terminal/safe-env.ts +60 -1
  602. package/src/tools/tool-manifest.ts +2 -0
  603. package/src/tools/types.ts +107 -21
  604. package/src/tools/ui-surface/definitions.ts +6 -5
  605. package/src/tts/__tests__/provider-adapters.test.ts +76 -2
  606. package/src/tts/providers/elevenlabs-provider.ts +75 -1
  607. package/src/types/onboarding-context.ts +2 -0
  608. package/src/util/errors.ts +17 -0
  609. package/src/util/platform.ts +10 -0
  610. package/src/watcher/__tests__/engine.test.ts +22 -0
  611. package/src/watcher/engine.ts +6 -2
  612. package/src/workspace/migrations/057-repair-stale-gemini-model-ids.ts +80 -15
  613. package/src/workspace/migrations/072-seed-reply-suggestion-callsite.ts +35 -22
  614. package/src/workspace/migrations/073-repair-recall-callsite-empty-profile.ts +3 -1
  615. package/src/workspace/migrations/083-system-prompt-prefix-to-file.ts +191 -0
  616. package/src/workspace/migrations/084-remove-legacy-skills-index.ts +276 -0
  617. package/src/workspace/migrations/085-memory-v2-bm25-b-reembed-disabled-v2-pages.ts +137 -0
  618. package/src/workspace/migrations/086-revert-stale-gemini-mis-rewrites.ts +198 -0
  619. package/src/workspace/migrations/087-memory-router-balanced-profile.ts +91 -0
  620. package/src/workspace/migrations/registry.ts +10 -0
  621. package/src/workspace/migrations/runner.ts +39 -9
  622. package/src/workspace/migrations/types.ts +4 -0
  623. package/examples/plugins/echo/bun.lock +0 -25
  624. package/src/__tests__/context-window-manager.test.ts +0 -2481
  625. package/src/__tests__/guardian-action-conversation-turn.test.ts +0 -441
  626. package/src/context/__tests__/compact-prompt.test.ts +0 -63
  627. package/src/context/prompts/compact.md +0 -26
  628. package/src/memory/graph/__tests__/remember-description.test.ts +0 -55
  629. package/src/prompts/__tests__/build-cli-reference-section.test.ts +0 -37
  630. package/src/runtime/guardian-action-conversation-turn.ts +0 -99
@@ -33,6 +33,7 @@ import { resolveCallSiteConfig } from "../config/llm-resolver.js";
33
33
  import { getConfig } from "../config/loader.js";
34
34
  import type { LLMCallSite } from "../config/schemas/llm.js";
35
35
  import type { ContextWindowConfig } from "../config/types.js";
36
+ import { runEmergencyCompaction } from "../context/compactor.js";
36
37
  import {
37
38
  derefToolResultReReads,
38
39
  postTurnTruncateToolResults,
@@ -42,6 +43,7 @@ import {
42
43
  getCalibrationProviderKey,
43
44
  } from "../context/token-estimator.js";
44
45
  import type { ContextWindowManager } from "../context/window-manager.js";
46
+ import { getDocumentsForConversation } from "../documents/document-store.js";
45
47
  import type { ToolProfiler } from "../events/tool-profiling-listener.js";
46
48
  import { writeRelationshipState } from "../home/relationship-state-writer.js";
47
49
  import {
@@ -69,7 +71,9 @@ import {
69
71
  isReplaceableTitle,
70
72
  queueRegenerateConversationTitle,
71
73
  } from "../memory/conversation-title-service.js";
74
+ import { isBackgroundConversationType } from "../memory/conversation-types.js";
72
75
  import type { ConversationGraphMemory } from "../memory/graph/conversation-graph-memory.js";
76
+ import { backfillMessageIdOnLogs } from "../memory/llm-request-log-store.js";
73
77
  import { recordMemoryRecallLog } from "../memory/memory-recall-log-store.js";
74
78
  import { enqueueMemoryRetrospectiveOnCompaction } from "../memory/memory-retrospective-enqueue.js";
75
79
  import { PKB_WORKSPACE_SCOPE } from "../memory/pkb/types.js";
@@ -79,6 +83,8 @@ import {
79
83
  shouldExposePersonalMemory,
80
84
  } from "../memory/v2/static-context.js";
81
85
  import type { PermissionPrompter } from "../permissions/prompter.js";
86
+ import { HOOKS } from "../plugin-api/constants.js";
87
+ import type { UserPromptSubmitContext } from "../plugin-api/types.js";
82
88
  import { defaultCompactionTerminal } from "../plugins/defaults/compaction.js";
83
89
  import { defaultHistoryRepairTerminal } from "../plugins/defaults/history-repair.js";
84
90
  import {
@@ -90,7 +96,7 @@ import {
90
96
  import { defaultPersistenceTerminal } from "../plugins/defaults/persistence.js";
91
97
  import { defaultTitleGenerateTerminal } from "../plugins/defaults/title-generate.js";
92
98
  import { defaultTokenEstimateTerminal } from "../plugins/defaults/token-estimate.js";
93
- import { DEFAULT_TIMEOUTS, runPipeline } from "../plugins/pipeline.js";
99
+ import { DEFAULT_TIMEOUTS, runHook, runPipeline } from "../plugins/pipeline.js";
94
100
  import { getMiddlewaresFor } from "../plugins/registry.js";
95
101
  import type {
96
102
  CircuitBreakerArgs,
@@ -105,6 +111,7 @@ import type {
105
111
  MemoryResult,
106
112
  OverflowReduceArgs,
107
113
  OverflowReduceResult,
114
+ PersistAddResult,
108
115
  PersistArgs,
109
116
  PersistResult,
110
117
  TurnContext as PluginTurnContext,
@@ -124,6 +131,7 @@ import type { Provider } from "../providers/types.js";
124
131
  import { resolveActorTrust } from "../runtime/actor-trust-resolver.js";
125
132
  import { broadcastMessage } from "../runtime/assistant-event-hub.js";
126
133
  import { DAEMON_INTERNAL_ASSISTANT_ID } from "../runtime/assistant-scope.js";
134
+ import { publishConversationMessagesChanged } from "../runtime/sync/resource-sync-events.js";
127
135
  import { redactSecrets } from "../security/secret-scanner.js";
128
136
  import { getSubagentManager } from "../subagent/index.js";
129
137
  import type { UsageActor } from "../usage/actors.js";
@@ -202,6 +210,10 @@ import type {
202
210
  } from "./message-protocol.js";
203
211
  import type { MemoryRecalled } from "./message-types/memory.js";
204
212
  import type { ConfirmationStateChanged } from "./message-types/messages.js";
213
+ import {
214
+ conversationMetadataSyncTag,
215
+ SYNC_TAGS,
216
+ } from "./message-types/sync.js";
205
217
  import { parseActualTokensFromError } from "./parse-actual-tokens-from-error.js";
206
218
  import type { TraceEmitter } from "./trace-emitter.js";
207
219
  import type { TrustContext } from "./trust-context.js";
@@ -455,6 +467,15 @@ export interface AgentLoopConversationContext {
455
467
  readonly contextWindowManager: ContextWindowManager;
456
468
  contextCompactedMessageCount: number;
457
469
  contextCompactedAt: number | null;
470
+ /**
471
+ * Set by `applyCompactionResult` when compaction strips runtime injections
472
+ * from the preserved tail. The next agent loop turn promotes this into a
473
+ * `compactedThisTurn` signal so NOW.md, PKB, and the v2 static block are
474
+ * re-injected on the first turn following `/compact` (which runs outside
475
+ * the agent loop and so has no other way to surface that compaction
476
+ * happened just before this turn).
477
+ */
478
+ pendingPostCompactReinject: boolean;
458
479
  /** Tracks consecutive compaction failures (summary LLM call threw). */
459
480
  consecutiveCompactionFailures: number;
460
481
  /** Timestamp (ms since epoch) until which the circuit breaker is open. */
@@ -767,6 +788,18 @@ export async function runAgentLoopImpl(
767
788
 
768
789
  ctx.profiler.startRequest();
769
790
  let turnStarted = false;
791
+ const state = createEventHandlerState();
792
+ let persistedErrorAssistantMessage = false;
793
+
794
+ const publishLoopMessagesChanged = (): void => {
795
+ if (
796
+ state.lastAssistantMessageId ||
797
+ state.persistedToolUseIds.size > 0 ||
798
+ persistedErrorAssistantMessage
799
+ ) {
800
+ publishConversationMessagesChanged(ctx.conversationId);
801
+ }
802
+ };
770
803
 
771
804
  // Populate Sentry scope with conversation-specific tags so any exception
772
805
  // captured during this turn (e.g. inside agent/loop.ts) can be
@@ -871,6 +904,13 @@ export async function runAgentLoopImpl(
871
904
  conversationId: ctx.conversationId,
872
905
  title,
873
906
  });
907
+ onEvent({
908
+ type: "sync_changed",
909
+ tags: [
910
+ SYNC_TAGS.conversationsList,
911
+ conversationMetadataSyncTag(ctx.conversationId),
912
+ ],
913
+ });
874
914
  },
875
915
  };
876
916
  setTimeout(() => {
@@ -892,8 +932,14 @@ export async function runAgentLoopImpl(
892
932
  }
893
933
 
894
934
  const isFirstMessage = ctx.messages.length === 1;
895
- let shouldInjectWorkspace = isFirstMessage;
896
- let compactedThisTurn = false;
935
+ // Promote a pending post-compaction re-inject signal (e.g. from `/compact`)
936
+ // into `compactedThisTurn` so NOW.md / PKB / v2 static blocks land on this
937
+ // turn even when no mid-turn compaction fires. Clear the flag immediately
938
+ // so this fires exactly once per `/compact` event.
939
+ const consumedPostCompactReinject = ctx.pendingPostCompactReinject;
940
+ ctx.pendingPostCompactReinject = false;
941
+ let shouldInjectWorkspace = isFirstMessage || consumedPostCompactReinject;
942
+ let compactedThisTurn = consumedPostCompactReinject;
897
943
  let slackCompactedThisTurn = false;
898
944
  const isSlackConversation = ctx.channelCapabilities?.channel === "slack";
899
945
  let currentSlackContextSummary =
@@ -1101,8 +1147,6 @@ export async function runAgentLoopImpl(
1101
1147
  }
1102
1148
  }
1103
1149
 
1104
- const state = createEventHandlerState();
1105
-
1106
1150
  // Register confirmation outcome tracker so the agent loop can link
1107
1151
  // confirmation decisions to tool_use_ids for persistence.
1108
1152
  ctx.onConfirmationOutcome = (
@@ -1328,6 +1372,20 @@ export async function runAgentLoopImpl(
1328
1372
  }
1329
1373
  }
1330
1374
 
1375
+ // Query active documents for this conversation so the injector chain
1376
+ // can surface them to the assistant (prevents duplicate document_create
1377
+ // calls when existing documents should be targeted with document_update).
1378
+ const conversationDocs = getDocumentsForConversation(ctx.conversationId);
1379
+ const activeDocuments =
1380
+ conversationDocs.length > 0
1381
+ ? conversationDocs.map((d) => ({
1382
+ surfaceId: d.surfaceId,
1383
+ title: d.title,
1384
+ wordCount: d.wordCount,
1385
+ updatedAt: d.updatedAt,
1386
+ }))
1387
+ : null;
1388
+
1331
1389
  ctx.refreshWorkspaceTopLevelContextIfNeeded();
1332
1390
 
1333
1391
  // Compute fresh turn timestamp for date grounding.
@@ -1429,9 +1487,13 @@ export async function runAgentLoopImpl(
1429
1487
  // are never stripped on normal turns — this preserves the cached prefix.
1430
1488
  // PKB/NOW content is sourced from the `memoryRetrieval` pipeline above
1431
1489
  // so plugins can override either source without touching the agent loop.
1432
- const currentNowContent = personalMemoryAllowed
1433
- ? memoryResult.nowContent
1434
- : null;
1490
+ // NOW.md injection can be disabled via `memory.retrieval.scratchpadInjection.enabled`.
1491
+ const scratchpadInjectionEnabled =
1492
+ getConfig().memory.retrieval.scratchpadInjection.enabled;
1493
+ const currentNowContent =
1494
+ personalMemoryAllowed && scratchpadInjectionEnabled
1495
+ ? memoryResult.nowContent
1496
+ : null;
1435
1497
  const shouldInjectNowAndPkb = isFirstMessage || compactedThisTurn;
1436
1498
  const nowScratchpad = shouldInjectNowAndPkb ? currentNowContent : null;
1437
1499
 
@@ -1535,6 +1597,7 @@ export async function runAgentLoopImpl(
1535
1597
  const injectionOpts = {
1536
1598
  diskPressureContext,
1537
1599
  activeSurface,
1600
+ activeDocuments,
1538
1601
  workspaceTopLevelContext: shouldInjectWorkspace
1539
1602
  ? ctx.workspaceTopLevelContext
1540
1603
  : null,
@@ -1556,6 +1619,9 @@ export async function runAgentLoopImpl(
1556
1619
  transportHints: ctx.transportHints ?? null,
1557
1620
  slackRuntimeContextNotice: ctx.slackRuntimeContextNotice ?? null,
1558
1621
  isNonInteractive: !isInteractiveResolved,
1622
+ isBackgroundConversation: isBackgroundConversationType(
1623
+ turnStartConversation?.conversationType,
1624
+ ),
1559
1625
  subagentStatusBlock,
1560
1626
  slackChronologicalMessages,
1561
1627
  slackActiveThreadFocusBlock,
@@ -1968,6 +2034,30 @@ export async function runAgentLoopImpl(
1968
2034
  runMessages = webSearchStrip.messages;
1969
2035
  }
1970
2036
 
2037
+ // user-prompt-submit hook: plugins may transform `runMessages` right
2038
+ // before the agent loop receives them. Fires once per user turn at
2039
+ // the primary `agentLoop.run` only — the re-entry / retry calls
2040
+ // further down in this function do not refire it (they're not new
2041
+ // user submissions). Plugins may mutate `ctx.latestMessages` in place
2042
+ // OR return a new context with a fresh array; `runHook` forwards
2043
+ // whichever the chain settles on. Order is plugin registration order.
2044
+ //
2045
+ // Fires BEFORE `preRunHistoryLength` is captured so the boundary
2046
+ // between pre-existing and hook-emitted messages — consumed by the
2047
+ // ordering-error retry gate, the post-run reconcile loop, and the
2048
+ // new-message extraction for persistence — reflects exactly what
2049
+ // `agentLoop.run` receives.
2050
+ const userPromptCtx: UserPromptSubmitContext = {
2051
+ conversationId: ctx.conversationId,
2052
+ originalMessages: ctx.messages,
2053
+ latestMessages: runMessages,
2054
+ };
2055
+ const finalUserPromptCtx = await runHook(
2056
+ HOOKS.USER_PROMPT_SUBMIT,
2057
+ userPromptCtx,
2058
+ );
2059
+ runMessages = finalUserPromptCtx.latestMessages;
2060
+
1971
2061
  let preRunHistoryLength = runMessages.length;
1972
2062
 
1973
2063
  const shouldGenerateTitle = isReplaceableTitle(
@@ -2408,6 +2498,64 @@ export async function runAgentLoopImpl(
2408
2498
  }
2409
2499
  }
2410
2500
 
2501
+ // ── Emergency mid-turn compaction ────────────────────────────
2502
+ // Before entering the reducer tier loop, attempt a targeted
2503
+ // emergency compaction: summarize everything before the last
2504
+ // tool_use + tool_result pair and let the agent continue with
2505
+ // [summary, last_tool_call, last_tool_result]. This preserves
2506
+ // the agent's most recent action context while aggressively
2507
+ // compressing history. Falls through to reducer tiers on failure.
2508
+ {
2509
+ try {
2510
+ const emergencyConfig = getConfig().compaction;
2511
+ const emergencyResult = await runEmergencyCompaction({
2512
+ conversationId: ctx.conversationId,
2513
+ messages: ctx.messages,
2514
+ provider: ctx.provider,
2515
+ systemPrompt: ctx.systemPrompt,
2516
+ tools: undefined,
2517
+ compaction: emergencyConfig,
2518
+ maxInputTokens: effectiveContextWindow.maxInputTokens,
2519
+ previousEstimatedInputTokens: estimatedTokensAtOverflow,
2520
+ force: true,
2521
+ signal: abortController.signal,
2522
+ overrideProfile: turnOverrideProfile ?? null,
2523
+ nonPersistedPrefixCount:
2524
+ ctx.contextWindowManager.nonPersistedPrefixCount,
2525
+ });
2526
+ if (emergencyResult.compacted) {
2527
+ rlog.info(
2528
+ {
2529
+ phase: "convergence",
2530
+ compactedMessages: emergencyResult.compactedMessages,
2531
+ summaryChars: emergencyResult.summaryText.length,
2532
+ },
2533
+ "Emergency mid-turn compaction succeeded — bypassing reducer tiers",
2534
+ );
2535
+ if (emergencyResult.summaryFailed !== undefined) {
2536
+ await trackCompactionOutcome(
2537
+ ctx,
2538
+ emergencyResult.summaryFailed,
2539
+ onEvent,
2540
+ );
2541
+ }
2542
+ if (emergencyResult.compacted) {
2543
+ await applySuccessfulCompaction(emergencyResult, ctx.messages);
2544
+ shouldInjectWorkspace = true;
2545
+ }
2546
+ // Clear the overflow flag and re-run the agent loop with
2547
+ // the compacted context.
2548
+ state.contextTooLargeDetected = false;
2549
+ }
2550
+ } catch (err) {
2551
+ rlog.warn(
2552
+ { phase: "convergence", err },
2553
+ "Emergency mid-turn compaction failed; continuing to reducer tiers",
2554
+ );
2555
+ }
2556
+ // If emergency compaction failed, fall through to reducer tiers.
2557
+ }
2558
+
2411
2559
  let convergenceAttempts = 0;
2412
2560
  const maxAttempts = overflowRecovery.maxAttempts;
2413
2561
 
@@ -2800,7 +2948,7 @@ export async function runAgentLoopImpl(
2800
2948
  const errorAssistantMessage = createAssistantMessage(
2801
2949
  state.providerErrorUserMessage,
2802
2950
  );
2803
- await runPipeline<PersistArgs, PersistResult>(
2951
+ const errorPersistResult = (await runPipeline<PersistArgs, PersistResult>(
2804
2952
  "persistence",
2805
2953
  getMiddlewaresFor("persistence"),
2806
2954
  defaultPersistenceTerminal,
@@ -2813,8 +2961,30 @@ export async function runAgentLoopImpl(
2813
2961
  },
2814
2962
  buildPluginTurnContext(ctx, reqId),
2815
2963
  DEFAULT_TIMEOUTS.persistence,
2816
- );
2964
+ )) as PersistAddResult;
2965
+ persistedErrorAssistantMessage = true;
2817
2966
  newMessages.push(errorAssistantMessage);
2967
+ // Pipe the just-assigned message id into any orphaned LLM request log
2968
+ // row(s) for this turn. The success path links rows via
2969
+ // `handleMessageComplete` -> `backfillMessageIdOnLogs`, but provider-
2970
+ // failure turns never fire `message_complete` (the synthetic assistant
2971
+ // message is persisted directly above), so without this call the rows
2972
+ // from `handleProviderError` stay with `message_id IS NULL` and a
2973
+ // later turn's backfill sweep would wrong-attach them to that turn's
2974
+ // assistant message. Scope is per-conversation, so concurrent runs on
2975
+ // other conversations cannot collide. Non-fatal — a DB hiccup must
2976
+ // not escalate a provider rejection into a turn-level throw.
2977
+ try {
2978
+ backfillMessageIdOnLogs(
2979
+ ctx.conversationId,
2980
+ errorPersistResult.message.id,
2981
+ );
2982
+ } catch (err) {
2983
+ rlog.warn(
2984
+ { err },
2985
+ "Failed to backfill message_id on provider-error LLM request logs (non-fatal)",
2986
+ );
2987
+ }
2818
2988
  // Do NOT send assistant_text_delta here — handleProviderError already
2819
2989
  // emitted a conversation_error event for this same error text, and the
2820
2990
  // client renders it as an InlineChatErrorAlert. Sending a text delta
@@ -2889,7 +3059,6 @@ export async function runAgentLoopImpl(
2889
3059
  convForDisk.createdAt,
2890
3060
  );
2891
3061
  };
2892
-
2893
3062
  // Fast-path: when the user cancelled, skip expensive post-loop work
2894
3063
  // (attachment resolution) and emit the cancellation event immediately
2895
3064
  // so the client can re-enable the UI without delay.
@@ -2908,6 +3077,7 @@ export async function runAgentLoopImpl(
2908
3077
  type: "generation_cancelled",
2909
3078
  conversationId: ctx.conversationId,
2910
3079
  });
3080
+ publishLoopMessagesChanged();
2911
3081
  } else {
2912
3082
  // Resolve attachments (only when not cancelled — this is expensive async I/O)
2913
3083
  const attachmentResult = await resolveAssistantAttachments(
@@ -2948,6 +3118,7 @@ export async function runAgentLoopImpl(
2948
3118
  type: "generation_cancelled",
2949
3119
  conversationId: ctx.conversationId,
2950
3120
  });
3121
+ publishLoopMessagesChanged();
2951
3122
  } else if (yieldedForHandoff) {
2952
3123
  ctx.traceEmitter.emit(
2953
3124
  "generation_handoff",
@@ -2976,6 +3147,7 @@ export async function runAgentLoopImpl(
2976
3147
  ? { displayMessageId: clientDisplayMessageId }
2977
3148
  : {}),
2978
3149
  });
3150
+ publishLoopMessagesChanged();
2979
3151
  } else {
2980
3152
  ctx.emitActivityState("idle", "message_complete", "global", reqId);
2981
3153
  ctx.traceEmitter.emit(
@@ -3002,6 +3174,7 @@ export async function runAgentLoopImpl(
3002
3174
  ? { displayMessageId: clientDisplayMessageId }
3003
3175
  : {}),
3004
3176
  });
3177
+ publishLoopMessagesChanged();
3005
3178
 
3006
3179
  // Proactive artifact: fire once when the processed turn was the 4th user message.
3007
3180
  // Only trigger for real user-authored turns (not subagent/system messages).
@@ -3056,6 +3229,13 @@ export async function runAgentLoopImpl(
3056
3229
  conversationId: ctx.conversationId,
3057
3230
  title,
3058
3231
  });
3232
+ onEvent({
3233
+ type: "sync_changed",
3234
+ tags: [
3235
+ SYNC_TAGS.conversationsList,
3236
+ conversationMetadataSyncTag(ctx.conversationId),
3237
+ ],
3238
+ });
3059
3239
  },
3060
3240
  signal: abortController.signal,
3061
3241
  });
@@ -3080,6 +3260,7 @@ export async function runAgentLoopImpl(
3080
3260
  type: "generation_cancelled",
3081
3261
  conversationId: ctx.conversationId,
3082
3262
  });
3263
+ publishLoopMessagesChanged();
3083
3264
  } else {
3084
3265
  ctx.emitActivityState("idle", "error_terminal", "global", reqId);
3085
3266
  const message = err instanceof Error ? err.message : String(err);
@@ -3104,6 +3285,7 @@ export async function runAgentLoopImpl(
3104
3285
  errorCategory: classified.errorCategory,
3105
3286
  });
3106
3287
  onEvent(buildConversationErrorMessage(ctx.conversationId, classified));
3288
+ publishLoopMessagesChanged();
3107
3289
  }
3108
3290
  } finally {
3109
3291
  if (turnStarted) {
@@ -3234,6 +3416,7 @@ export interface CompactionApplyContext {
3234
3416
  messages: Message[];
3235
3417
  contextCompactedMessageCount: number;
3236
3418
  contextCompactedAt: number | null;
3419
+ pendingPostCompactReinject: boolean;
3237
3420
  readonly graphMemory: ConversationGraphMemory;
3238
3421
  readonly provider: Provider;
3239
3422
  usageStats: UsageStats;
@@ -3283,6 +3466,10 @@ export async function applyCompactionResult(
3283
3466
  ctx.contextCompactedMessageCount += result.compactedPersistedMessages;
3284
3467
  const compactedAt = Date.now();
3285
3468
  ctx.contextCompactedAt = compactedAt;
3469
+ // Signal to the next agent loop turn that NOW.md / PKB / v2 static blocks
3470
+ // were stripped from the tail and need fresh re-injection. Consumed and
3471
+ // cleared at the top of the next `runAgentLoopImpl` run.
3472
+ ctx.pendingPostCompactReinject = true;
3286
3473
  await ctx.graphMemory.onCompacted(result.compactedPersistedMessages);
3287
3474
  updateConversationContextWindow(
3288
3475
  ctx.conversationId,