@vellumai/assistant 0.8.6 → 0.8.7

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 (891) hide show
  1. package/AGENTS.md +4 -4
  2. package/Dockerfile +1 -0
  3. package/bun.lock +11 -2
  4. package/docker-entrypoint.sh +8 -6
  5. package/docs/plugins.md +63 -28
  6. package/examples/plugins/echo/register.ts +4 -7
  7. package/knip.json +1 -0
  8. package/node_modules/@vellumai/environments/bun.lock +24 -0
  9. package/node_modules/@vellumai/environments/package.json +18 -0
  10. package/node_modules/@vellumai/environments/src/__tests__/package-boundary.test.ts +95 -0
  11. package/node_modules/@vellumai/environments/src/index.ts +11 -0
  12. package/node_modules/@vellumai/environments/src/seeds.ts +73 -0
  13. package/node_modules/@vellumai/environments/src/types.ts +70 -0
  14. package/node_modules/@vellumai/environments/tsconfig.json +20 -0
  15. package/node_modules/@vellumai/skill-host-contracts/src/assistant-event.ts +11 -0
  16. package/node_modules/@vellumai/skill-host-contracts/src/client.ts +3 -4
  17. package/node_modules/@vellumai/skill-host-contracts/src/skill-host.ts +6 -2
  18. package/openapi.yaml +3735 -353
  19. package/package.json +7 -3
  20. package/scripts/generate-openapi.ts +20 -13
  21. package/src/__tests__/agent-loop-callsite-precedence.test.ts +42 -80
  22. package/src/__tests__/agent-loop-exit-reason.test.ts +240 -39
  23. package/src/__tests__/agent-loop-mutable-latest-user-message.test.ts +141 -0
  24. package/src/__tests__/agent-loop-override-profile.test.ts +19 -32
  25. package/src/__tests__/agent-loop-provider-error-recording.test.ts +6 -4
  26. package/src/__tests__/agent-loop-thinking.test.ts +17 -12
  27. package/src/__tests__/agent-loop.test.ts +207 -341
  28. package/src/__tests__/agent-wake-disk-pressure-callsite.test.ts +4 -2
  29. package/src/__tests__/agent-wake-override-profile.test.ts +22 -40
  30. package/src/__tests__/anthropic-provider.test.ts +201 -55
  31. package/src/__tests__/app-builder-skill-instructions.test.ts +22 -0
  32. package/src/__tests__/app-control-flow.test.ts +5 -0
  33. package/src/__tests__/approval-cascade.test.ts +4 -11
  34. package/src/__tests__/approval-routes-http.test.ts +4 -2
  35. package/src/__tests__/assistant-event.test.ts +15 -0
  36. package/src/__tests__/assistant-feature-flags-integration.test.ts +2 -2
  37. package/src/__tests__/avatar-e2e.test.ts +7 -37
  38. package/src/__tests__/avatar-generator.test.ts +12 -42
  39. package/src/__tests__/avatar-identity-sync.test.ts +28 -3
  40. package/src/__tests__/background-shell-bash.test.ts +3 -7
  41. package/src/__tests__/btw-routes.test.ts +7 -12
  42. package/src/__tests__/call-pointer-messages.test.ts +5 -3
  43. package/src/__tests__/call-site-routing-provider.test.ts +22 -40
  44. package/src/__tests__/catalog-files.test.ts +1 -0
  45. package/src/__tests__/channel-approval-routes.test.ts +48 -20
  46. package/src/__tests__/channel-approvals.test.ts +3 -1
  47. package/src/__tests__/channel-invite-transport.test.ts +1 -5
  48. package/src/__tests__/channel-readiness-routes.test.ts +0 -4
  49. package/src/__tests__/channel-readiness-slack-remote.test.ts +2 -7
  50. package/src/__tests__/channel-retry-sweep.test.ts +71 -79
  51. package/src/__tests__/circuit-breaker-pipeline.test.ts +3 -3
  52. package/src/__tests__/clawhub-files.test.ts +1 -0
  53. package/src/__tests__/compaction-events.test.ts +5 -17
  54. package/src/__tests__/compaction-pipeline.test.ts +1 -1
  55. package/src/__tests__/compaction-timeout-recovery.test.ts +37 -48
  56. package/src/__tests__/compaction-trail-store.test.ts +1 -79
  57. package/src/__tests__/compactor-image-manifest-trust.test.ts +112 -0
  58. package/src/__tests__/computer-use-tools.test.ts +2 -2
  59. package/src/__tests__/config-watcher.test.ts +28 -0
  60. package/src/__tests__/context-search-agent-runner.test.ts +6 -3
  61. package/src/__tests__/context-token-estimator.test.ts +34 -0
  62. package/src/__tests__/context-window-manager-compact-retry.test.ts +291 -0
  63. package/src/__tests__/conversation-abort-tool-results.test.ts +14 -7
  64. package/src/__tests__/conversation-agent-loop-disk-pressure.test.ts +3 -2
  65. package/src/__tests__/conversation-agent-loop-inference-profile.test.ts +12 -27
  66. package/src/__tests__/conversation-agent-loop-overflow.test.ts +430 -90
  67. package/src/__tests__/conversation-agent-loop.test.ts +581 -62
  68. package/src/__tests__/conversation-analysis-routes.test.ts +1 -3
  69. package/src/__tests__/conversation-app-control-lifecycle.test.ts +1 -1
  70. package/src/__tests__/conversation-clear-safety.test.ts +20 -10
  71. package/src/__tests__/conversation-confirmation-signals.test.ts +15 -45
  72. package/src/__tests__/conversation-disk-view-integration.test.ts +2 -2
  73. package/src/__tests__/conversation-disk-view.test.ts +10 -17
  74. package/src/__tests__/conversation-fork-crud.test.ts +86 -172
  75. package/src/__tests__/conversation-fork-route.test.ts +16 -14
  76. package/src/__tests__/conversation-init.benchmark.test.ts +6 -6
  77. package/src/__tests__/conversation-lifecycle.test.ts +3 -2
  78. package/src/__tests__/conversation-load-history-repair.test.ts +3 -2
  79. package/src/__tests__/conversation-load-history-stripped.test.ts +1 -1
  80. package/src/__tests__/conversation-message-sync-tags.test.ts +3 -4
  81. package/src/__tests__/conversation-pairing.test.ts +34 -4
  82. package/src/__tests__/conversation-pre-run-repair.test.ts +1 -1
  83. package/src/__tests__/conversation-process-app-control-preactivation.test.ts +4 -0
  84. package/src/__tests__/conversation-process-callsite.test.ts +27 -30
  85. package/src/__tests__/conversation-provider-retry-repair.test.ts +53 -44
  86. package/src/__tests__/conversation-queue.test.ts +270 -164
  87. package/src/__tests__/conversation-routes-disk-view.test.ts +3 -2
  88. package/src/__tests__/conversation-routes-guardian-reply.test.ts +2 -2
  89. package/src/__tests__/conversation-routes-slash-commands.test.ts +2 -2
  90. package/src/__tests__/conversation-runtime-assembly.test.ts +20 -22
  91. package/src/__tests__/conversation-runtime-workspace.test.ts +19 -1
  92. package/src/__tests__/conversation-slash-queue.test.ts +37 -31
  93. package/src/__tests__/conversation-slash-unknown.test.ts +13 -15
  94. package/src/__tests__/conversation-speed-override.test.ts +8 -22
  95. package/src/__tests__/conversation-stream-state.test.ts +484 -0
  96. package/src/__tests__/conversation-surfaces-action-delivery.test.ts +6 -15
  97. package/src/__tests__/conversation-surfaces-app-control.test.ts +32 -4
  98. package/src/__tests__/conversation-surfaces-state-update.test.ts +5 -2
  99. package/src/__tests__/conversation-surfaces-table-action.test.ts +6 -15
  100. package/src/__tests__/conversation-tool-setup-app-refresh.test.ts +23 -11
  101. package/src/__tests__/conversation-unread-route.test.ts +14 -2
  102. package/src/__tests__/conversation-usage.test.ts +0 -2
  103. package/src/__tests__/conversation-wipe.test.ts +1 -1
  104. package/src/__tests__/conversation-workspace-cache-state.test.ts +3 -1
  105. package/src/__tests__/conversation-workspace-injection.test.ts +48 -22
  106. package/src/__tests__/conversation-workspace-tool-tracking.test.ts +27 -7
  107. package/src/__tests__/credential-execution-tools.test.ts +1 -2
  108. package/src/__tests__/credential-security-invariants.test.ts +0 -1
  109. package/src/__tests__/cross-provider-web-search.test.ts +6 -2
  110. package/src/__tests__/cu-unified-flow.test.ts +26 -1
  111. package/src/__tests__/db-schedule-syntax-migration.test.ts +11 -0
  112. package/src/__tests__/disk-pressure-guard.test.ts +66 -0
  113. package/src/__tests__/disk-pressure-routes.test.ts +9 -2
  114. package/src/__tests__/dm-persistence.test.ts +7 -2
  115. package/src/__tests__/dynamic-page-surface.test.ts +68 -0
  116. package/src/__tests__/edit-propagation.test.ts +1 -2
  117. package/src/__tests__/empty-response-pipeline.test.ts +127 -5
  118. package/src/__tests__/filing-service.test.ts +2 -2
  119. package/src/__tests__/first-greeting.test.ts +55 -14
  120. package/src/__tests__/gemini-inline-media.test.ts +78 -0
  121. package/src/__tests__/gemini-provider.test.ts +351 -28
  122. package/src/__tests__/guardian-routing-state.test.ts +60 -71
  123. package/src/__tests__/handlers-user-message-approval-consumption.test.ts +9 -7
  124. package/src/__tests__/heartbeat-disk-pressure.test.ts +1 -0
  125. package/src/__tests__/heartbeat-service.test.ts +2 -1
  126. package/src/__tests__/history-repair-hook.test.ts +161 -0
  127. package/src/__tests__/history-repair-observability.test.ts +1 -1
  128. package/src/__tests__/history-repair.test.ts +2 -1
  129. package/src/__tests__/host-app-control-proxy.test.ts +2 -0
  130. package/src/__tests__/host-cu-proxy.test.ts +2 -0
  131. package/src/__tests__/host-file-edit-tool.test.ts +4 -2
  132. package/src/__tests__/host-file-proxy.test.ts +31 -0
  133. package/src/__tests__/host-file-read-tool.test.ts +4 -2
  134. package/src/__tests__/host-file-write-tool.test.ts +9 -3
  135. package/src/__tests__/host-proxy-preactivation.test.ts +53 -14
  136. package/src/__tests__/host-shell-tool.test.ts +9 -4
  137. package/src/__tests__/http-user-message-parity.test.ts +2 -2
  138. package/src/__tests__/identity-intro-cache.test.ts +35 -14
  139. package/src/__tests__/inbound-slack-persistence.test.ts +7 -2
  140. package/src/__tests__/injector-background-turn.test.ts +1 -1
  141. package/src/__tests__/injector-chain.test.ts +1 -1
  142. package/src/__tests__/injector-disk-pressure.test.ts +1 -1
  143. package/src/__tests__/injector-document-comments.test.ts +1 -1
  144. package/src/__tests__/injector-pkb-v2-silenced.test.ts +1 -1
  145. package/src/__tests__/injector-v3-suppression.test.ts +220 -0
  146. package/src/__tests__/list-messages-attachments.test.ts +7 -8
  147. package/src/__tests__/list-messages-hidden-metadata.test.ts +17 -15
  148. package/src/__tests__/list-messages-page-latest.test.ts +0 -1
  149. package/src/__tests__/list-messages-tool-merge.test.ts +36 -6
  150. package/src/__tests__/llm-call-pipeline.test.ts +21 -15
  151. package/src/__tests__/llm-request-log-turn-query.test.ts +42 -86
  152. package/src/__tests__/llm-resolver.test.ts +23 -47
  153. package/src/__tests__/llm-usage-store.test.ts +45 -0
  154. package/src/__tests__/log-export-routes.test.ts +59 -0
  155. package/src/__tests__/managed-skill-lifecycle.test.ts +1 -8
  156. package/src/__tests__/mcp-auth-routes.test.ts +15 -10
  157. package/src/__tests__/mcp-health-check.test.ts +18 -13
  158. package/src/__tests__/memory-retrieval-pipeline.test.ts +1 -1
  159. package/src/__tests__/memory-v2-static-injector.test.ts +1 -1
  160. package/src/__tests__/messaging-send-tool.test.ts +8 -4
  161. package/src/__tests__/migration-export-http.test.ts +12 -12
  162. package/src/__tests__/migration-import-commit-http.test.ts +8 -8
  163. package/src/__tests__/migration-import-preflight-http.test.ts +7 -7
  164. package/src/__tests__/migration-validate-http.test.ts +3 -3
  165. package/src/__tests__/native-web-search.test.ts +14 -20
  166. package/src/__tests__/notification-decision-identity.test.ts +9 -18
  167. package/src/__tests__/notification-decision-recipient-context.test.ts +3 -6
  168. package/src/__tests__/oauth-commands-routes.test.ts +1 -1
  169. package/src/__tests__/onboarding-template-contract.test.ts +10 -0
  170. package/src/__tests__/openai-provider.test.ts +66 -70
  171. package/src/__tests__/openai-responses-provider.test.ts +21 -77
  172. package/src/__tests__/outbound-slack-persistence.test.ts +2 -1
  173. package/src/__tests__/overflow-reduce-pipeline.test.ts +2 -4
  174. package/src/__tests__/parallel-tool.benchmark.test.ts +24 -36
  175. package/src/__tests__/persistence-pipeline.test.ts +15 -26
  176. package/src/__tests__/persistence-secret-redaction.test.ts +2 -1
  177. package/src/__tests__/pipeline-runner.test.ts +2 -3
  178. package/src/__tests__/plugin-bootstrap.test.ts +51 -25
  179. package/src/__tests__/plugin-route-contribution.test.ts +6 -16
  180. package/src/__tests__/plugin-skill-contribution.test.ts +7 -17
  181. package/src/__tests__/plugin-tool-contribution.test.ts +10 -26
  182. package/src/__tests__/plugin-types.test.ts +7 -14
  183. package/src/__tests__/prechat-onboarding-contract.test.ts +23 -0
  184. package/src/__tests__/process-message-background-slack.test.ts +17 -16
  185. package/src/__tests__/process-message-display-content.test.ts +30 -42
  186. package/src/__tests__/provider-commit-message-generator.test.ts +19 -14
  187. package/src/__tests__/provider-error-scenarios.test.ts +7 -6
  188. package/src/__tests__/provider-platform-proxy-integration.test.ts +3 -8
  189. package/src/__tests__/provider-send-message-override-profile.test.ts +9 -25
  190. package/src/__tests__/provider-streaming.benchmark.test.ts +12 -22
  191. package/src/__tests__/provider-usage-tracking.test.ts +0 -6
  192. package/src/__tests__/ratelimit.test.ts +9 -4
  193. package/src/__tests__/relay-server.test.ts +20 -13
  194. package/src/__tests__/retry-openrouter-only-normalization.test.ts +5 -8
  195. package/src/__tests__/retry-thinking-tool-choice.test.ts +10 -13
  196. package/src/__tests__/retry-verbosity-normalization.test.ts +5 -8
  197. package/src/__tests__/runtime-events-sse-reconnect.test.ts +353 -0
  198. package/src/__tests__/schedule-routes.test.ts +80 -10
  199. package/src/__tests__/schedule-store.test.ts +67 -0
  200. package/src/__tests__/schedule-tools.test.ts +125 -0
  201. package/src/__tests__/secret-ingress-http.test.ts +2 -2
  202. package/src/__tests__/secret-prompt-log-hygiene.test.ts +11 -7
  203. package/src/__tests__/secret-prompter-channel-fallback.test.ts +11 -9
  204. package/src/__tests__/secret-response-routing.test.ts +13 -11
  205. package/src/__tests__/send-endpoint-busy.test.ts +2 -1
  206. package/src/__tests__/shell-observability.test.ts +249 -0
  207. package/src/__tests__/skill-feature-flags-integration.test.ts +11 -11
  208. package/src/__tests__/skill-feature-flags.test.ts +6 -6
  209. package/src/__tests__/skill-load-feature-flag.test.ts +10 -10
  210. package/src/__tests__/skills-files-catalog-fallback.test.ts +10 -0
  211. package/src/__tests__/skillssh-files.test.ts +1 -0
  212. package/src/__tests__/starter-task-flow.test.ts +6 -6
  213. package/src/__tests__/strip-memory-injections.test.ts +102 -14
  214. package/src/__tests__/subagent-call-site-routing.test.ts +2 -2
  215. package/src/__tests__/suggestion-routes.test.ts +3 -3
  216. package/src/__tests__/sync-message-contract.test.ts +19 -16
  217. package/src/__tests__/system-prompt.test.ts +54 -0
  218. package/src/__tests__/terminal-tools.test.ts +3 -24
  219. package/src/__tests__/thread-backfill.test.ts +4 -9
  220. package/src/__tests__/title-generate-pipeline.test.ts +1 -1
  221. package/src/__tests__/token-estimate-pipeline.test.ts +2 -4
  222. package/src/__tests__/tool-error-pipeline.test.ts +2 -2
  223. package/src/__tests__/tool-execute-pipeline.test.ts +1 -1
  224. package/src/__tests__/tool-preview-lifecycle.test.ts +13 -11
  225. package/src/__tests__/tool-result-truncate-pipeline.test.ts +9 -12
  226. package/src/__tests__/tool-result-truncation.test.ts +3 -1
  227. package/src/__tests__/tools-audio-read.test.ts +113 -0
  228. package/src/__tests__/turn-boundary-resolution.test.ts +44 -84
  229. package/src/__tests__/turn-events-store.test.ts +11 -7
  230. package/src/__tests__/voice-scoped-grant-consumer.test.ts +8 -6
  231. package/src/__tests__/voice-session-bridge.test.ts +13 -7
  232. package/src/acp/__tests__/prepare-agent-env.test.ts +143 -31
  233. package/src/acp/prepare-agent-env.ts +52 -11
  234. package/src/agent/compaction-circuit.ts +140 -0
  235. package/src/agent/loop.ts +409 -85
  236. package/src/api/README.md +19 -17
  237. package/src/api/constants/tool-execution.ts +21 -0
  238. package/src/api/events/assistant-activity-state.ts +75 -0
  239. package/src/api/events/assistant-outbound-attachment.ts +25 -27
  240. package/src/api/events/assistant-text-delta.ts +6 -8
  241. package/src/api/events/assistant-turn-start.ts +5 -7
  242. package/src/api/events/avatar-updated.ts +24 -0
  243. package/src/api/events/compaction-circuit-closed.ts +26 -0
  244. package/src/api/events/compaction-circuit-open.ts +28 -0
  245. package/src/api/events/confirmation-request.ts +114 -0
  246. package/src/api/events/contact-request.ts +33 -0
  247. package/src/api/events/conversation-error.ts +77 -0
  248. package/src/api/events/conversation-list-invalidated.ts +38 -0
  249. package/src/api/events/conversation-title-updated.ts +24 -0
  250. package/src/api/events/disk-pressure-status-changed.ts +61 -0
  251. package/src/api/events/document-comment-created.ts +24 -28
  252. package/src/api/events/document-comment-deleted.ts +6 -8
  253. package/src/api/events/document-comment-reopened.ts +6 -8
  254. package/src/api/events/document-comment-resolved.ts +8 -10
  255. package/src/api/events/document-editor-update.ts +27 -0
  256. package/src/api/events/error.ts +32 -0
  257. package/src/api/events/generation-cancelled.ts +4 -6
  258. package/src/api/events/generation-handoff.ts +13 -15
  259. package/src/api/events/home-feed-updated.ts +26 -0
  260. package/src/api/events/identity-changed.ts +32 -0
  261. package/src/api/events/interaction-resolved.ts +50 -0
  262. package/src/api/events/message-complete.ts +10 -12
  263. package/src/api/events/message-dequeued.ts +21 -0
  264. package/src/api/events/message-queued-deleted.ts +23 -0
  265. package/src/api/events/message-queued.ts +22 -0
  266. package/src/api/events/message-request-complete.ts +29 -0
  267. package/src/api/events/navigate-settings.ts +20 -0
  268. package/src/api/events/notification-intent.ts +33 -0
  269. package/src/api/events/open-url.ts +6 -8
  270. package/src/api/events/question-request.ts +67 -0
  271. package/src/api/events/relationship-state-updated.ts +4 -6
  272. package/src/api/events/secret-request.ts +42 -0
  273. package/src/api/events/subagent-event.ts +79 -0
  274. package/src/api/events/subagent-spawned.ts +40 -0
  275. package/src/api/events/subagent-status-changed.ts +65 -0
  276. package/src/api/events/sync-changed.ts +29 -0
  277. package/src/api/events/tool-result.ts +129 -0
  278. package/src/api/events/tool-use-start.ts +8 -10
  279. package/src/api/events/turn-profile-auto-routed.ts +28 -0
  280. package/src/api/events/ui-surface-complete.ts +30 -0
  281. package/src/api/events/ui-surface-dismiss.ts +22 -0
  282. package/src/api/events/ui-surface-show.ts +67 -0
  283. package/src/api/events/ui-surface-update.ts +26 -0
  284. package/src/api/events/usage-update.ts +34 -0
  285. package/src/api/events/user-message-echo.ts +35 -0
  286. package/src/api/index.ts +354 -0
  287. package/src/api/requests/dictation.ts +45 -0
  288. package/src/api/responses/disk-pressure-status.ts +26 -0
  289. package/src/api/responses/home.ts +217 -0
  290. package/src/api/responses/llm-context-response.ts +2 -0
  291. package/src/api/responses/memory-v3-selection-log.ts +50 -0
  292. package/src/api/responses/subagent-detail.ts +48 -0
  293. package/src/approvals/guardian-decision-primitive.ts +7 -15
  294. package/src/approvals/guardian-request-resolvers.ts +6 -9
  295. package/src/avatar/__tests__/avatar-manifest.test.ts +236 -0
  296. package/src/avatar/__tests__/avatar-store.test.ts +193 -0
  297. package/src/avatar/avatar-manifest.ts +195 -0
  298. package/src/avatar/avatar-store.ts +113 -0
  299. package/src/avatar/traits-png-sync.ts +8 -2
  300. package/src/background-wake/next-wake.test.ts +31 -1
  301. package/src/background-wake/next-wake.ts +4 -1
  302. package/src/calls/call-conversation-messages.ts +6 -4
  303. package/src/calls/guardian-action-sweep.ts +6 -4
  304. package/src/calls/relay-server.ts +12 -8
  305. package/src/calls/voice-session-bridge.ts +13 -27
  306. package/src/cli/commands/__tests__/memory-v3.test.ts +245 -0
  307. package/src/cli/commands/avatar.ts +17 -11
  308. package/src/cli/commands/conversations.ts +15 -1
  309. package/src/cli/commands/db/__tests__/repair.test.ts +540 -0
  310. package/src/cli/commands/db/__tests__/status.test.ts +253 -0
  311. package/src/cli/commands/db/format.ts +48 -0
  312. package/src/cli/commands/db/index.ts +29 -0
  313. package/src/cli/commands/db/repair-step-conversation-backfill.ts +345 -0
  314. package/src/cli/commands/db/repair-step-integrity.ts +146 -0
  315. package/src/cli/commands/db/repair-steps.ts +164 -0
  316. package/src/cli/commands/db/repair.ts +141 -0
  317. package/src/cli/commands/db/status.ts +366 -0
  318. package/src/cli/commands/memory-v3.ts +159 -445
  319. package/src/cli/lib/cli-colors.ts +24 -6
  320. package/src/cli/program.ts +4 -5
  321. package/src/config/__tests__/feature-flag-registry-guard.test.ts +2 -2
  322. package/src/config/assistant-feature-flags.ts +2 -2
  323. package/src/config/bundled-skills/app-builder/SKILL.md +14 -3
  324. package/src/config/bundled-skills/media-processing/services/reduce.ts +6 -9
  325. package/src/config/bundled-skills/messaging/tools/messaging-send.ts +7 -2
  326. package/src/config/bundled-skills/schedule/SKILL.md +1 -1
  327. package/src/config/bundled-skills/schedule/TOOLS.json +8 -0
  328. package/src/config/call-site-defaults.ts +2 -7
  329. package/src/config/feature-flag-registry.json +25 -9
  330. package/src/config/schemas/__tests__/memory-v2.test.ts +1 -226
  331. package/src/config/schemas/call-site-catalog.ts +8 -15
  332. package/src/config/schemas/llm.ts +2 -3
  333. package/src/config/schemas/memory-lifecycle.ts +24 -0
  334. package/src/config/schemas/memory-v2.ts +0 -253
  335. package/src/config/schemas/memory-v3.ts +39 -0
  336. package/src/config/schemas/memory.ts +6 -1
  337. package/src/config/schemas/timeouts.ts +3 -1
  338. package/src/context/compactor.ts +54 -31
  339. package/src/context/token-estimator.ts +19 -0
  340. package/src/context/tool-result-truncation.ts +1 -43
  341. package/src/context/window-manager.ts +138 -20
  342. package/src/daemon/__tests__/conversation-surfaces-launch.test.ts +2 -2
  343. package/src/daemon/__tests__/web-search-status-text.test.ts +10 -6
  344. package/src/daemon/approval-generators.ts +4 -4
  345. package/src/daemon/config-watcher.ts +7 -1
  346. package/src/daemon/conversation-agent-loop-handlers.ts +225 -88
  347. package/src/daemon/conversation-agent-loop.ts +284 -584
  348. package/src/daemon/conversation-error.ts +7 -7
  349. package/src/daemon/conversation-history.ts +22 -6
  350. package/src/daemon/conversation-launch.ts +4 -8
  351. package/src/daemon/conversation-lifecycle.ts +10 -38
  352. package/src/daemon/conversation-messaging.ts +1 -3
  353. package/src/daemon/conversation-notifiers.ts +7 -5
  354. package/src/daemon/conversation-process.ts +100 -79
  355. package/src/daemon/conversation-runtime-assembly.ts +47 -21
  356. package/src/daemon/conversation-store.ts +6 -5
  357. package/src/daemon/conversation-surfaces.ts +55 -69
  358. package/src/daemon/conversation-tool-setup.ts +3 -0
  359. package/src/daemon/conversation.ts +91 -126
  360. package/src/daemon/daemon-skill-host.ts +2 -6
  361. package/src/daemon/disk-pressure-guard.ts +35 -29
  362. package/src/daemon/external-plugins-bootstrap.ts +46 -24
  363. package/src/daemon/first-greeting.ts +26 -4
  364. package/src/daemon/guardian-action-generators.ts +2 -2
  365. package/src/daemon/handlers/conversations.ts +6 -22
  366. package/src/daemon/handlers/shared.ts +4 -0
  367. package/src/daemon/handlers/skills.ts +15 -14
  368. package/src/daemon/host-app-control-proxy.ts +54 -1
  369. package/src/daemon/host-cu-proxy.ts +46 -22
  370. package/src/daemon/host-file-proxy.ts +25 -1
  371. package/src/daemon/host-proxy-preactivation.ts +25 -6
  372. package/src/daemon/lifecycle.ts +28 -55
  373. package/src/daemon/message-protocol.ts +2 -3
  374. package/src/daemon/message-provenance.ts +49 -0
  375. package/src/daemon/message-types/contacts.ts +3 -20
  376. package/src/daemon/message-types/conversations.ts +13 -111
  377. package/src/daemon/message-types/documents.ts +3 -9
  378. package/src/daemon/message-types/home.ts +4 -17
  379. package/src/daemon/message-types/integrations.ts +2 -6
  380. package/src/daemon/message-types/messages.ts +28 -343
  381. package/src/daemon/message-types/notifications.ts +2 -32
  382. package/src/daemon/message-types/settings.ts +3 -8
  383. package/src/daemon/message-types/skills.ts +2 -0
  384. package/src/daemon/message-types/surfaces.ts +2 -0
  385. package/src/daemon/message-types/sync.ts +12 -25
  386. package/src/daemon/message-types/workspace.ts +3 -11
  387. package/src/daemon/process-message.ts +49 -46
  388. package/src/daemon/server.ts +12 -0
  389. package/src/daemon/tool-side-effects.ts +10 -7
  390. package/src/daemon/trust-context.ts +13 -0
  391. package/src/daemon/wake-target-adapter.ts +11 -1
  392. package/src/heartbeat/__tests__/heartbeat-service.test.ts +3 -1
  393. package/src/heartbeat/heartbeat-run-store.ts +31 -0
  394. package/src/heartbeat/heartbeat-service.ts +16 -0
  395. package/src/home/feature-gate.ts +22 -0
  396. package/src/home/feed-types.ts +36 -221
  397. package/src/ipc/__tests__/email-ipc.test.ts +0 -9
  398. package/src/ipc/routes/__tests__/route-adapter.test.ts +244 -0
  399. package/src/ipc/routes/route-adapter.ts +45 -6
  400. package/src/ipc/skill-routes/__tests__/memory.test.ts +18 -9
  401. package/src/ipc/skill-routes/__tests__/providers.test.ts +10 -10
  402. package/src/ipc/skill-routes/__tests__/registries.test.ts +28 -18
  403. package/src/ipc/skill-routes/memory.ts +26 -13
  404. package/src/ipc/skill-routes/providers.ts +5 -6
  405. package/src/ipc/skill-routes/registries.ts +13 -61
  406. package/src/live-voice/__tests__/live-voice-archive.test.ts +24 -11
  407. package/src/memory/__tests__/conversation-queries.test.ts +192 -8
  408. package/src/memory/__tests__/db-maintenance.test.ts +128 -0
  409. package/src/memory/__tests__/jobs-store-job-classes.test.ts +5 -4
  410. package/src/memory/__tests__/memory-retrospective-job.test.ts +10 -6
  411. package/src/memory/__tests__/memory-v3-selections-migration.test.ts +103 -0
  412. package/src/memory/context-search/agent-runner.ts +2 -4
  413. package/src/memory/conversation-crud.ts +39 -8
  414. package/src/memory/conversation-queries.ts +78 -22
  415. package/src/memory/db-init.ts +8 -0
  416. package/src/memory/db-maintenance.ts +18 -2
  417. package/src/memory/graph/consolidation.ts +8 -11
  418. package/src/memory/graph/conversation-graph-memory.ts +41 -8
  419. package/src/memory/graph/extraction.ts +6 -9
  420. package/src/memory/graph/narrative.ts +2 -2
  421. package/src/memory/graph/pattern-scan.ts +2 -2
  422. package/src/memory/graph/retriever.ts +20 -26
  423. package/src/memory/graph/tools.ts +4 -4
  424. package/src/memory/job-handlers/conversation-starters.ts +32 -32
  425. package/src/memory/job-handlers/summarization.ts +1 -2
  426. package/src/memory/jobs-store.ts +3 -1
  427. package/src/memory/jobs-worker.ts +51 -39
  428. package/src/memory/llm-request-log-source-clickhouse.ts +5 -31
  429. package/src/memory/llm-request-log-source-local.ts +0 -11
  430. package/src/memory/llm-request-log-source.ts +9 -25
  431. package/src/memory/llm-request-log-store.ts +0 -41
  432. package/src/memory/llm-usage-store.ts +10 -0
  433. package/src/memory/memory-marker.ts +17 -0
  434. package/src/memory/memory-retrospective-job.ts +6 -2
  435. package/src/memory/memory-v2-activation-log-store.ts +1 -83
  436. package/src/memory/migrations/267-llm-usage-events-add-assistant-version.ts +46 -0
  437. package/src/memory/migrations/268-add-memory-v3-selections.ts +28 -0
  438. package/src/memory/migrations/269-schedule-script-timeout.ts +11 -0
  439. package/src/memory/migrations/270-messages-role-created-at-index.ts +18 -0
  440. package/src/memory/migrations/__tests__/267-llm-usage-events-add-assistant-version.test.ts +117 -0
  441. package/src/memory/migrations/index.ts +4 -0
  442. package/src/memory/schema/infrastructure.ts +11 -0
  443. package/src/memory/v2/__tests__/consolidation-job.test.ts +124 -0
  444. package/src/memory/v2/__tests__/migration.test.ts +11 -3
  445. package/src/memory/v2/__tests__/page-index.test.ts +37 -1
  446. package/src/memory/v2/__tests__/router.test.ts +14 -4
  447. package/src/memory/v2/__tests__/sweep-job.test.ts +6 -5
  448. package/src/memory/v2/backfill-jobs.ts +6 -0
  449. package/src/memory/v2/consolidation-job.ts +89 -9
  450. package/src/memory/v2/migration.ts +5 -3
  451. package/src/memory/v2/page-index.ts +11 -0
  452. package/src/memory/v2/router.ts +8 -11
  453. package/src/memory/v2/sweep-job.ts +8 -11
  454. package/src/memory/v2/types.ts +1 -0
  455. package/src/memory/v3/__tests__/assign.test.ts +242 -0
  456. package/src/memory/v3/__tests__/capabilities.test.ts +118 -0
  457. package/src/memory/v3/__tests__/core.test.ts +39 -0
  458. package/src/memory/v3/__tests__/fixtures/eval-turns.json +36 -0
  459. package/src/memory/v3/__tests__/fixtures/live-turns.json +37 -0
  460. package/src/memory/v3/__tests__/health.test.ts +203 -0
  461. package/src/memory/v3/__tests__/live-integration.test.ts +330 -0
  462. package/src/memory/v3/__tests__/maintain-job.test.ts +288 -0
  463. package/src/memory/v3/__tests__/needle.test.ts +107 -0
  464. package/src/memory/v3/__tests__/orchestrate.test.ts +400 -0
  465. package/src/memory/v3/__tests__/reconcile.test.ts +274 -0
  466. package/src/memory/v3/__tests__/render-injection.test.ts +61 -0
  467. package/src/memory/v3/__tests__/router.test.ts +260 -0
  468. package/src/memory/v3/__tests__/selection-log-store.test.ts +179 -0
  469. package/src/memory/v3/__tests__/selector.test.ts +404 -0
  470. package/src/memory/v3/__tests__/shadow-plugin.test.ts +414 -0
  471. package/src/memory/v3/__tests__/snapshot.test.ts +168 -0
  472. package/src/memory/v3/__tests__/tree.test.ts +192 -0
  473. package/src/memory/v3/__tests__/types.test.ts +54 -0
  474. package/src/memory/v3/__tests__/working-set-eviction.test.ts +106 -0
  475. package/src/memory/v3/__tests__/working-set-skeleton.test.ts +44 -0
  476. package/src/memory/v3/assign.ts +268 -0
  477. package/src/memory/v3/capabilities.ts +124 -0
  478. package/src/memory/v3/core.ts +26 -0
  479. package/src/memory/v3/data/README.md +84 -0
  480. package/src/memory/v3/data/assignments.json +5 -0
  481. package/src/memory/v3/data/core.json +1 -0
  482. package/src/memory/v3/data/leaves/domain-a/topic-x.md +9 -0
  483. package/src/memory/v3/data/leaves/domain-a/topic-y.md +9 -0
  484. package/src/memory/v3/data/leaves/domain-b/topic-z.md +9 -0
  485. package/src/memory/v3/health.ts +0 -0
  486. package/src/memory/v3/maintain-job.ts +314 -0
  487. package/src/memory/v3/needle.ts +115 -0
  488. package/src/memory/v3/orchestrate.ts +114 -0
  489. package/src/memory/v3/page-content.ts +34 -0
  490. package/src/memory/v3/provider-blocks.ts +16 -0
  491. package/src/memory/v3/reconcile.ts +523 -0
  492. package/src/memory/v3/render-injection.ts +32 -0
  493. package/src/memory/v3/router.ts +184 -0
  494. package/src/memory/v3/selection-log-store.ts +84 -0
  495. package/src/memory/v3/selector.ts +211 -0
  496. package/src/memory/v3/shadow-plugin.ts +379 -0
  497. package/src/memory/v3/snapshot.ts +209 -0
  498. package/src/memory/v3/tree.ts +174 -0
  499. package/src/memory/v3/types.ts +46 -60
  500. package/src/memory/v3/working-set.ts +88 -0
  501. package/src/messaging/providers/slack/render-transcript.test.ts +1 -1
  502. package/src/messaging/providers/slack/render-transcript.ts +2 -2
  503. package/src/messaging/style-analyzer.ts +8 -11
  504. package/src/notifications/conversation-pairing.ts +8 -6
  505. package/src/notifications/decision-engine.ts +10 -13
  506. package/src/notifications/preference-extractor.ts +11 -14
  507. package/src/permissions/prompter.ts +42 -36
  508. package/src/permissions/question-prompter.test.ts +35 -26
  509. package/src/permissions/question-prompter.ts +6 -10
  510. package/src/plugin-api/index.ts +2 -0
  511. package/src/plugin-api/types.ts +25 -3
  512. package/src/plugins/defaults/circuit-breaker/middlewares/circuitBreaker.ts +93 -0
  513. package/src/plugins/defaults/circuit-breaker/package.json +15 -0
  514. package/src/plugins/defaults/circuit-breaker/register.ts +39 -0
  515. package/src/plugins/defaults/compaction/middlewares/compaction.ts +25 -0
  516. package/src/plugins/defaults/compaction/package.json +15 -0
  517. package/src/plugins/defaults/compaction/register.ts +35 -0
  518. package/src/plugins/defaults/compaction/terminal.ts +73 -0
  519. package/src/plugins/defaults/empty-response/middlewares/emptyResponse.ts +22 -0
  520. package/src/plugins/defaults/empty-response/package.json +15 -0
  521. package/src/plugins/defaults/empty-response/register.ts +28 -0
  522. package/src/plugins/defaults/empty-response/terminal.ts +106 -0
  523. package/src/plugins/defaults/history-repair/hooks/user-prompt-submit.ts +35 -0
  524. package/src/plugins/defaults/history-repair/package.json +15 -0
  525. package/src/plugins/defaults/history-repair/register.ts +24 -0
  526. package/src/{daemon/history-repair.ts → plugins/defaults/history-repair/terminal.ts} +48 -35
  527. package/src/plugins/defaults/index.ts +29 -40
  528. package/src/plugins/defaults/injectors/package.json +15 -0
  529. package/src/plugins/defaults/{injectors.ts → injectors/register.ts} +14 -38
  530. package/src/plugins/defaults/llm-call/middlewares/llmCall.ts +17 -0
  531. package/src/plugins/defaults/llm-call/package.json +15 -0
  532. package/src/plugins/defaults/{llm-call.ts → llm-call/register.ts} +6 -38
  533. package/src/plugins/defaults/memory-retrieval/middlewares/memoryRetrieval.ts +17 -0
  534. package/src/plugins/defaults/memory-retrieval/package.json +15 -0
  535. package/src/plugins/defaults/{memory-retrieval.ts → memory-retrieval/register.ts} +10 -48
  536. package/src/plugins/defaults/{overflow-reduce.ts → overflow-reduce/middlewares/overflowReduce.ts} +18 -77
  537. package/src/plugins/defaults/overflow-reduce/package.json +15 -0
  538. package/src/plugins/defaults/overflow-reduce/register.ts +42 -0
  539. package/src/plugins/defaults/persistence/middlewares/persistence.ts +19 -0
  540. package/src/plugins/defaults/persistence/package.json +15 -0
  541. package/src/plugins/defaults/persistence/register.ts +38 -0
  542. package/src/plugins/defaults/persistence/terminal.ts +83 -0
  543. package/src/plugins/defaults/title-generate/package.json +15 -0
  544. package/src/plugins/defaults/title-generate/register.ts +35 -0
  545. package/src/plugins/defaults/title-generate/terminal.ts +31 -0
  546. package/src/plugins/defaults/token-estimate/middlewares/tokenEstimate.ts +23 -0
  547. package/src/plugins/defaults/token-estimate/package.json +15 -0
  548. package/src/plugins/defaults/token-estimate/register.ts +34 -0
  549. package/src/plugins/defaults/token-estimate/terminal.ts +40 -0
  550. package/src/plugins/defaults/tool-error/middlewares/toolError.ts +21 -0
  551. package/src/plugins/defaults/tool-error/package.json +15 -0
  552. package/src/plugins/defaults/tool-error/register.ts +35 -0
  553. package/src/plugins/defaults/tool-error/terminal.ts +47 -0
  554. package/src/plugins/defaults/tool-execute/middlewares/toolExecute.ts +23 -0
  555. package/src/plugins/defaults/tool-execute/package.json +15 -0
  556. package/src/plugins/defaults/{tool-execute.ts → tool-execute/register.ts} +8 -46
  557. package/src/plugins/defaults/tool-result-truncate/middlewares/toolResultTruncate.ts +23 -0
  558. package/src/plugins/defaults/tool-result-truncate/package.json +15 -0
  559. package/src/plugins/defaults/tool-result-truncate/register.ts +35 -0
  560. package/src/plugins/defaults/tool-result-truncate/terminal.ts +113 -0
  561. package/src/plugins/defaults/tool-result-truncate/types.ts +22 -0
  562. package/src/plugins/external-plugin-loader.ts +2 -2
  563. package/src/plugins/pipeline.ts +0 -12
  564. package/src/plugins/types.ts +51 -90
  565. package/src/plugins/user-loader.ts +4 -3
  566. package/src/proactive-artifact/aux-message-injector.ts +0 -1
  567. package/src/proactive-artifact/job.test.ts +20 -8
  568. package/src/proactive-artifact/job.ts +3 -1
  569. package/src/prompts/sections.ts +20 -7
  570. package/src/prompts/templates/BOOTSTRAP-CONTENT-AUTOMATION.md +2 -2
  571. package/src/prompts/templates/BOOTSTRAP.md +5 -1
  572. package/src/prompts/templates/system-sections.ts +6 -0
  573. package/src/providers/__tests__/retry-callsite.test.ts +25 -25
  574. package/src/providers/__tests__/satellite-connection-routing.test.ts +7 -21
  575. package/src/providers/anthropic/client.ts +24 -5
  576. package/src/providers/call-site-routing.ts +1 -9
  577. package/src/providers/gemini/client.ts +152 -34
  578. package/src/providers/gemini/inline-media.ts +74 -0
  579. package/src/providers/openai/__tests__/chat-completions-provider-reasoning.test.ts +0 -2
  580. package/src/providers/openai/chat-completions-provider.ts +1 -4
  581. package/src/providers/openai/responses-provider.ts +1 -4
  582. package/src/providers/openrouter/client.ts +1 -6
  583. package/src/providers/provider-send-message.ts +6 -6
  584. package/src/providers/ratelimit.ts +1 -9
  585. package/src/providers/retry.ts +0 -5
  586. package/src/providers/types.ts +11 -2
  587. package/src/providers/usage-tracking.ts +1 -9
  588. package/src/runtime/__tests__/agent-wake.test.ts +131 -26
  589. package/src/runtime/__tests__/background-job-runner.test.ts +1 -3
  590. package/src/runtime/agent-wake.ts +93 -18
  591. package/src/runtime/assistant-event-hub.ts +2 -2
  592. package/src/runtime/auth/__tests__/guard-tests.test.ts +75 -109
  593. package/src/runtime/auth/__tests__/route-policy.test.ts +153 -170
  594. package/src/runtime/auth/route-policy.ts +42 -1079
  595. package/src/runtime/background-job-runner.ts +1 -4
  596. package/src/runtime/btw-sidechain.ts +3 -1
  597. package/src/runtime/channel-approvals.ts +3 -14
  598. package/src/runtime/channel-invite-transport.ts +5 -6
  599. package/src/runtime/channel-readiness-service.ts +2 -5
  600. package/src/runtime/channel-retry-sweep.ts +12 -16
  601. package/src/runtime/conversation-stream-state.ts +294 -0
  602. package/src/runtime/http-router.ts +19 -22
  603. package/src/runtime/http-types.ts +12 -6
  604. package/src/runtime/invite-instruction-generator.ts +3 -3
  605. package/src/runtime/pending-interactions.ts +2 -2
  606. package/src/runtime/routes/__tests__/avatar-state-routes.test.ts +565 -0
  607. package/src/runtime/routes/__tests__/content-source-routes.test.ts +4 -4
  608. package/src/runtime/routes/__tests__/conversation-compaction-routes.test.ts +62 -32
  609. package/src/runtime/routes/__tests__/conversation-list-routes.test.ts +237 -0
  610. package/src/runtime/routes/__tests__/inference-provider-connection-routes.test.ts +13 -22
  611. package/src/runtime/routes/__tests__/memory-v2-simulate-route.test.ts +7 -2
  612. package/src/runtime/routes/__tests__/sanity-routes.test.ts +6 -6
  613. package/src/runtime/routes/__tests__/stt-routes.test.ts +3 -3
  614. package/src/runtime/routes/__tests__/suggest-trust-rule-routes.test.ts +5 -2
  615. package/src/runtime/routes/__tests__/tts-routes.test.ts +3 -3
  616. package/src/runtime/routes/acp-routes.test.ts +97 -75
  617. package/src/runtime/routes/acp-routes.ts +29 -6
  618. package/src/runtime/routes/app-management-routes.ts +97 -24
  619. package/src/runtime/routes/app-routes.ts +25 -5
  620. package/src/runtime/routes/approval-routes.ts +16 -4
  621. package/src/runtime/routes/attachment-routes.ts +25 -1
  622. package/src/runtime/routes/audio-routes.ts +1 -0
  623. package/src/runtime/routes/audit-routes.ts +5 -0
  624. package/src/runtime/routes/auth-routes.ts +5 -0
  625. package/src/runtime/routes/avatar-routes.ts +238 -59
  626. package/src/runtime/routes/background-tool-routes.ts +9 -0
  627. package/src/runtime/routes/background-wake-routes.ts +13 -3
  628. package/src/runtime/routes/backup-routes.ts +45 -0
  629. package/src/runtime/routes/bookmark-routes.ts +13 -0
  630. package/src/runtime/routes/brain-graph-routes.ts +9 -0
  631. package/src/runtime/routes/browser-routes.ts +5 -0
  632. package/src/runtime/routes/browser-tabs-routes.ts +5 -0
  633. package/src/runtime/routes/btw-routes.ts +5 -1
  634. package/src/runtime/routes/cache-routes.ts +13 -0
  635. package/src/runtime/routes/call-routes.ts +21 -10
  636. package/src/runtime/routes/channel-availability-routes.ts +5 -1
  637. package/src/runtime/routes/channel-readiness-routes.ts +37 -4
  638. package/src/runtime/routes/channel-route-definitions.ts +21 -0
  639. package/src/runtime/routes/channel-verification-routes.ts +21 -0
  640. package/src/runtime/routes/chatgpt-subscription-auth-routes.ts +9 -2
  641. package/src/runtime/routes/client-routes.ts +9 -0
  642. package/src/runtime/routes/consolidation-routes.ts +13 -5
  643. package/src/runtime/routes/contact-prompt-routes.ts +9 -0
  644. package/src/runtime/routes/contact-routes.ts +90 -23
  645. package/src/runtime/routes/content-source-routes.ts +5 -1
  646. package/src/runtime/routes/conversation-analysis-routes.ts +5 -1
  647. package/src/runtime/routes/conversation-attention-routes.ts +5 -0
  648. package/src/runtime/routes/conversation-cli-routes.ts +54 -7
  649. package/src/runtime/routes/conversation-compaction-routes.ts +54 -25
  650. package/src/runtime/routes/conversation-list-routes.ts +81 -12
  651. package/src/runtime/routes/conversation-management-routes.ts +57 -14
  652. package/src/runtime/routes/conversation-query-routes.ts +88 -41
  653. package/src/runtime/routes/conversation-routes.ts +74 -19
  654. package/src/runtime/routes/conversation-starter-routes.ts +22 -13
  655. package/src/runtime/routes/conversations-import-routes.ts +6 -1
  656. package/src/runtime/routes/credential-prompt-routes.ts +5 -0
  657. package/src/runtime/routes/credential-routes.ts +25 -6
  658. package/src/runtime/routes/debug-bash-routes.ts +5 -0
  659. package/src/runtime/routes/debug-routes.ts +11 -2
  660. package/src/runtime/routes/defer-routes.ts +13 -0
  661. package/src/runtime/routes/diagnostics-routes.ts +37 -46
  662. package/src/runtime/routes/disk-pressure-routes.ts +17 -31
  663. package/src/runtime/routes/document-comments-routes.ts +46 -27
  664. package/src/runtime/routes/documents-routes.ts +21 -10
  665. package/src/runtime/routes/domain-routes.ts +61 -28
  666. package/src/runtime/routes/email-routes.ts +33 -0
  667. package/src/runtime/routes/events-routes.ts +114 -9
  668. package/src/runtime/routes/filing-routes.ts +9 -4
  669. package/src/runtime/routes/gateway-log-routes.ts +5 -0
  670. package/src/runtime/routes/global-search-routes.ts +53 -50
  671. package/src/runtime/routes/group-routes.ts +21 -5
  672. package/src/runtime/routes/guardian-action-routes.ts +9 -0
  673. package/src/runtime/routes/guardian-approval-interception.ts +0 -31
  674. package/src/runtime/routes/heartbeat-routes.ts +25 -9
  675. package/src/runtime/routes/home-feed-routes.ts +23 -19
  676. package/src/runtime/routes/home-state-routes.ts +8 -40
  677. package/src/runtime/routes/host-app-control-routes.ts +5 -0
  678. package/src/runtime/routes/host-bash-routes.ts +5 -0
  679. package/src/runtime/routes/host-browser-routes.ts +13 -0
  680. package/src/runtime/routes/host-cu-routes.ts +5 -0
  681. package/src/runtime/routes/host-file-routes.ts +26 -6
  682. package/src/runtime/routes/host-transfer-routes.ts +13 -2
  683. package/src/runtime/routes/http-adapter.ts +1 -2
  684. package/src/runtime/routes/identity-intro-cache.ts +17 -6
  685. package/src/runtime/routes/identity-routes.ts +12 -2
  686. package/src/runtime/routes/image-generation-routes.ts +5 -0
  687. package/src/runtime/routes/inbound-message-handler.ts +15 -11
  688. package/src/runtime/routes/inbound-stages/background-dispatch.test.ts +0 -12
  689. package/src/runtime/routes/inbound-stages/background-dispatch.ts +15 -19
  690. package/src/runtime/routes/inference-profile-session-routes.ts +13 -3
  691. package/src/runtime/routes/inference-provider-connection-routes.ts +21 -5
  692. package/src/runtime/routes/inference-send-routes.ts +11 -11
  693. package/src/runtime/routes/integrations/a2a.ts +30 -7
  694. package/src/runtime/routes/integrations/slack/channel.ts +19 -3
  695. package/src/runtime/routes/integrations/slack/share.ts +9 -2
  696. package/src/runtime/routes/integrations/telegram.ts +28 -9
  697. package/src/runtime/routes/integrations/twilio.ts +35 -7
  698. package/src/runtime/routes/integrations/vercel.ts +3 -3
  699. package/src/runtime/routes/internal-oauth-routes.ts +5 -0
  700. package/src/runtime/routes/internal-twilio-routes.ts +13 -0
  701. package/src/runtime/routes/llm-call-sites-routes.ts +39 -4
  702. package/src/runtime/routes/log-export-routes.ts +28 -10
  703. package/src/runtime/routes/mcp-auth-routes.ts +25 -0
  704. package/src/runtime/routes/memory-item-routes.ts +21 -10
  705. package/src/runtime/routes/memory-v2-routes.ts +90 -36
  706. package/src/runtime/routes/memory-v3-routes.ts +273 -407
  707. package/src/runtime/routes/migration-rollback-routes.ts +5 -1
  708. package/src/runtime/routes/migration-routes.ts +29 -0
  709. package/src/runtime/routes/notification-routes.ts +17 -1
  710. package/src/runtime/routes/oauth-apps.ts +33 -11
  711. package/src/runtime/routes/oauth-commands-routes.ts +37 -14
  712. package/src/runtime/routes/oauth-connect-routes.ts +9 -0
  713. package/src/runtime/routes/oauth-lifecycle-routes.ts +5 -1
  714. package/src/runtime/routes/oauth-providers.ts +35 -10
  715. package/src/runtime/routes/platform-routes.ts +21 -0
  716. package/src/runtime/routes/playground/__tests__/force-compact.test.ts +3 -2
  717. package/src/runtime/routes/playground/__tests__/inject-failures.test.ts +37 -16
  718. package/src/runtime/routes/playground/__tests__/reset-circuit.test.ts +7 -3
  719. package/src/runtime/routes/playground/__tests__/state.test.ts +10 -3
  720. package/src/runtime/routes/playground/force-compact.ts +1 -1
  721. package/src/runtime/routes/playground/helpers.ts +0 -1
  722. package/src/runtime/routes/playground/inject-failures.ts +13 -8
  723. package/src/runtime/routes/playground/reset-circuit.ts +14 -9
  724. package/src/runtime/routes/playground/seed-conversation.ts +1 -1
  725. package/src/runtime/routes/playground/seeded-conversations.ts +3 -3
  726. package/src/runtime/routes/playground/state.ts +4 -3
  727. package/src/runtime/routes/plugins-routes.ts +22 -19
  728. package/src/runtime/routes/profiler-routes.ts +17 -4
  729. package/src/runtime/routes/ps-routes.ts +5 -0
  730. package/src/runtime/routes/publish-routes.ts +13 -3
  731. package/src/runtime/routes/question-routes.ts +5 -0
  732. package/src/runtime/routes/recording-routes.ts +25 -12
  733. package/src/runtime/routes/rename-conversation-routes.ts +5 -0
  734. package/src/runtime/routes/sanity-routes.ts +9 -2
  735. package/src/runtime/routes/schedule-routes.ts +137 -47
  736. package/src/runtime/routes/secret-routes.ts +17 -4
  737. package/src/runtime/routes/sequence-routes.ts +33 -0
  738. package/src/runtime/routes/settings-routes.ts +65 -19
  739. package/src/runtime/routes/skills-routes.ts +133 -69
  740. package/src/runtime/routes/slack-channel-routes.ts +5 -0
  741. package/src/runtime/routes/stt-routes.ts +13 -6
  742. package/src/runtime/routes/subagents-routes.ts +24 -18
  743. package/src/runtime/routes/suggest-trust-rule-routes.ts +7 -2
  744. package/src/runtime/routes/surface-action-routes.ts +9 -0
  745. package/src/runtime/routes/surface-content-routes.ts +10 -2
  746. package/src/runtime/routes/task-routes.ts +37 -0
  747. package/src/runtime/routes/telemetry-routes.ts +9 -0
  748. package/src/runtime/routes/trace-event-routes.ts +42 -1
  749. package/src/runtime/routes/trust-rules-routes.ts +5 -0
  750. package/src/runtime/routes/tts-routes.ts +13 -6
  751. package/src/runtime/routes/types.ts +17 -8
  752. package/src/runtime/routes/ui-request-routes.ts +5 -0
  753. package/src/runtime/routes/upgrade-broadcast-routes.ts +5 -0
  754. package/src/runtime/routes/usage-routes.ts +71 -3
  755. package/src/runtime/routes/user-routes-cli.ts +9 -0
  756. package/src/runtime/routes/user-routes.ts +5 -1
  757. package/src/runtime/routes/wake-conversation-routes.ts +5 -0
  758. package/src/runtime/routes/watcher-routes.ts +21 -0
  759. package/src/runtime/routes/webhook-routes.ts +9 -0
  760. package/src/runtime/routes/wipe-conversation-routes.ts +5 -0
  761. package/src/runtime/routes/work-items-routes.ts +47 -19
  762. package/src/runtime/routes/workspace-commit-routes.ts +5 -0
  763. package/src/runtime/routes/workspace-routes.test.ts +42 -0
  764. package/src/runtime/routes/workspace-routes.ts +120 -9
  765. package/src/runtime/services/__tests__/analyze-conversation.test.ts +2 -4
  766. package/src/runtime/services/analyze-conversation.ts +3 -6
  767. package/src/runtime/services/conversation-serializer.ts +24 -2
  768. package/src/runtime/sync/resource-sync-events.ts +16 -2
  769. package/src/runtime/sync/sync-publisher.ts +2 -2
  770. package/src/schedule/run-script.ts +28 -3
  771. package/src/schedule/schedule-store.ts +8 -0
  772. package/src/schedule/scheduler.ts +3 -1
  773. package/src/signals/user-message.ts +5 -8
  774. package/src/skills/catalog-files.ts +4 -1
  775. package/src/skills/clawhub-files.ts +2 -0
  776. package/src/skills/skillssh-files.ts +2 -0
  777. package/src/subagent/manager.ts +3 -6
  778. package/src/telemetry/types.ts +26 -0
  779. package/src/telemetry/usage-telemetry-reporter.test.ts +138 -1
  780. package/src/telemetry/usage-telemetry-reporter.ts +31 -0
  781. package/src/tools/acp/spawn.test.ts +88 -38
  782. package/src/tools/apps/definitions.ts +8 -4
  783. package/src/tools/ask-question/ask-question-tool.test.ts +120 -105
  784. package/src/tools/ask-question/ask-question-tool.ts +85 -90
  785. package/src/tools/computer-use/definitions.ts +28 -24
  786. package/src/tools/credential-execution/make-authenticated-request.ts +56 -51
  787. package/src/tools/credential-execution/manage-secure-command-tool.ts +2 -2
  788. package/src/tools/credential-execution/run-authenticated-command.ts +82 -77
  789. package/src/tools/credentials/vault.ts +112 -111
  790. package/src/tools/execution-target.ts +1 -1
  791. package/src/tools/execution-timeout.ts +3 -4
  792. package/src/tools/filesystem/edit.ts +45 -42
  793. package/src/tools/filesystem/list.ts +33 -30
  794. package/src/tools/filesystem/read.ts +54 -35
  795. package/src/tools/filesystem/write.ts +34 -31
  796. package/src/tools/host-filesystem/edit.ts +44 -42
  797. package/src/tools/host-filesystem/read.ts +49 -35
  798. package/src/tools/host-filesystem/transfer.ts +121 -108
  799. package/src/tools/host-filesystem/write.ts +33 -31
  800. package/src/tools/host-terminal/host-shell.ts +50 -48
  801. package/src/tools/memory/register.ts +23 -24
  802. package/src/tools/network/web-fetch.ts +49 -46
  803. package/src/tools/network/web-search.ts +16 -13
  804. package/src/tools/registry.ts +39 -16
  805. package/src/tools/schedule/create.ts +11 -0
  806. package/src/tools/schedule/update.ts +16 -0
  807. package/src/tools/shared/filesystem/audio-read.ts +122 -0
  808. package/src/tools/shared/filesystem/image-read.ts +1 -1
  809. package/src/tools/skills/execute.ts +34 -31
  810. package/src/tools/skills/load.ts +29 -23
  811. package/src/tools/subagent/notify-parent.ts +35 -32
  812. package/src/tools/system/avatar-generator.ts +13 -22
  813. package/src/tools/system/request-permission.ts +30 -27
  814. package/src/tools/terminal/shell.ts +190 -61
  815. package/src/tools/tool-defaults.ts +20 -9
  816. package/src/tools/tool-manifest.ts +4 -4
  817. package/src/tools/types.ts +74 -23
  818. package/src/tools/ui-surface/definitions.ts +69 -9
  819. package/src/usage/types.ts +10 -0
  820. package/src/util/errors.ts +2 -2
  821. package/src/util/map-limit.ts +27 -0
  822. package/src/util/platform.ts +15 -12
  823. package/src/work-items/work-item-runner.ts +7 -2
  824. package/src/workspace/migrations/028-recover-conversations-from-disk-view.ts +7 -20
  825. package/src/workspace/migrations/092-backfill-v3-leaves.ts +169 -0
  826. package/src/workspace/migrations/093-backfill-leaf-ids.ts +144 -0
  827. package/src/workspace/migrations/094-seed-avatar-manifest.ts +155 -0
  828. package/src/workspace/migrations/__tests__/094-seed-avatar-manifest.test.ts +136 -0
  829. package/src/workspace/migrations/__tests__/backfill-leaf-ids.test.ts +175 -0
  830. package/src/workspace/migrations/__tests__/backfill-v3-leaves.test.ts +124 -0
  831. package/src/workspace/migrations/registry.ts +6 -0
  832. package/src/workspace/provider-commit-message-generator.ts +15 -17
  833. package/tsconfig.json +4 -1
  834. package/src/__tests__/history-repair-pipeline.test.ts +0 -396
  835. package/src/cli/commands/__tests__/memory-v3-render.test.ts +0 -340
  836. package/src/cli/commands/memory-v3-render.ts +0 -491
  837. package/src/daemon/message-types/disk-pressure.ts +0 -9
  838. package/src/email/feature-gate.ts +0 -23
  839. package/src/memory/v3/__tests__/coactivation-store.test.ts +0 -422
  840. package/src/memory/v3/__tests__/consolidation-job.test.ts +0 -466
  841. package/src/memory/v3/__tests__/coretrieval-seed.test.ts +0 -270
  842. package/src/memory/v3/__tests__/edge-learning-job.test.ts +0 -324
  843. package/src/memory/v3/__tests__/edges.test.ts +0 -706
  844. package/src/memory/v3/__tests__/filter.test.ts +0 -560
  845. package/src/memory/v3/__tests__/gate.test.ts +0 -637
  846. package/src/memory/v3/__tests__/index-composition.test.ts +0 -291
  847. package/src/memory/v3/__tests__/loop.test.ts +0 -775
  848. package/src/memory/v3/__tests__/retriever.test.ts +0 -226
  849. package/src/memory/v3/__tests__/scouts.test.ts +0 -489
  850. package/src/memory/v3/__tests__/shadow-diff.test.ts +0 -225
  851. package/src/memory/v3/__tests__/shadow-middleware.test.ts +0 -398
  852. package/src/memory/v3/__tests__/system-prompts.test.ts +0 -154
  853. package/src/memory/v3/__tests__/traversal.test.ts +0 -508
  854. package/src/memory/v3/__tests__/tree-index.test.ts +0 -280
  855. package/src/memory/v3/__tests__/tree-store.test.ts +0 -529
  856. package/src/memory/v3/__tests__/tree-walk.test.ts +0 -784
  857. package/src/memory/v3/__tests__/validate.test.ts +0 -277
  858. package/src/memory/v3/auto-edges.ts +0 -223
  859. package/src/memory/v3/coactivation-store.ts +0 -124
  860. package/src/memory/v3/consolidation-job.ts +0 -323
  861. package/src/memory/v3/coretrieval-seed.ts +0 -240
  862. package/src/memory/v3/edge-learning-job.ts +0 -160
  863. package/src/memory/v3/edges.ts +0 -286
  864. package/src/memory/v3/filter.ts +0 -286
  865. package/src/memory/v3/gate.ts +0 -349
  866. package/src/memory/v3/index-composition.ts +0 -126
  867. package/src/memory/v3/llm-capture.ts +0 -46
  868. package/src/memory/v3/loop.ts +0 -430
  869. package/src/memory/v3/maintenance.ts +0 -144
  870. package/src/memory/v3/prompt-context.ts +0 -33
  871. package/src/memory/v3/prompts/consolidation.ts +0 -458
  872. package/src/memory/v3/prompts/system-prompts.ts +0 -196
  873. package/src/memory/v3/retriever.ts +0 -33
  874. package/src/memory/v3/scouts.ts +0 -431
  875. package/src/memory/v3/shadow-diff.ts +0 -287
  876. package/src/memory/v3/shadow-middleware.ts +0 -347
  877. package/src/memory/v3/traversal.ts +0 -211
  878. package/src/memory/v3/tree-index.ts +0 -237
  879. package/src/memory/v3/tree-store.ts +0 -394
  880. package/src/memory/v3/tree-walk.ts +0 -356
  881. package/src/memory/v3/validate.ts +0 -323
  882. package/src/plugins/defaults/circuit-breaker.ts +0 -141
  883. package/src/plugins/defaults/compaction.ts +0 -141
  884. package/src/plugins/defaults/empty-response.ts +0 -124
  885. package/src/plugins/defaults/history-repair.ts +0 -83
  886. package/src/plugins/defaults/persistence.ts +0 -146
  887. package/src/plugins/defaults/title-generate.ts +0 -90
  888. package/src/plugins/defaults/token-estimate.ts +0 -101
  889. package/src/plugins/defaults/tool-error.ts +0 -119
  890. package/src/plugins/defaults/tool-result-truncate.ts +0 -84
  891. package/src/runtime/routes/__tests__/memory-v3-simulate-params.test.ts +0 -35
@@ -4,6 +4,7 @@
4
4
  * Do not store secrets here — use the credential store or protected/ directory.
5
5
  */
6
6
  import {
7
+ type Dirent,
7
8
  existsSync,
8
9
  mkdirSync,
9
10
  readdirSync,
@@ -18,6 +19,7 @@ import { basename, dirname, join } from "node:path";
18
19
  import { z } from "zod";
19
20
 
20
21
  import { getWorkspaceDir } from "../../util/platform.js";
22
+ import { ACTOR_PRINCIPALS } from "../auth/route-policy.js";
21
23
  import { publishSoundsConfigUpdated } from "../sync/resource-sync-events.js";
22
24
  import {
23
25
  BadRequestError,
@@ -33,13 +35,77 @@ import {
33
35
  resolveWorkspacePath,
34
36
  } from "./workspace-utils.js";
35
37
 
36
- interface TreeEntry {
37
- name: string;
38
- path: string;
39
- type: "file" | "directory";
40
- size: number | null;
41
- mimeType: string | null;
42
- modifiedAt: string;
38
+ const workspaceTreeEntrySchema = z.object({
39
+ name: z.string(),
40
+ path: z.string(),
41
+ type: z.enum(["file", "directory"]),
42
+ size: z.number().nullable(),
43
+ mimeType: z.string().nullable(),
44
+ modifiedAt: z.string(),
45
+ });
46
+
47
+ type TreeEntry = z.infer<typeof workspaceTreeEntrySchema>;
48
+
49
+ // Total number of filesystem entries we're willing to traverse when computing
50
+ // recursive directory sizes for a single tree listing. The budget is shared
51
+ // across every directory in the response so a giant `repos/` checkout cannot
52
+ // starve the request — once exhausted, remaining directories report `size:
53
+ // null` (caller renders an unknown-size placeholder). 50k is generous for
54
+ // typical workspaces (sounds, db, logs) while bailing fast on multi-repo
55
+ // trees.
56
+ const DIR_SIZE_TOTAL_ENTRY_BUDGET = 50_000;
57
+
58
+ interface DirSizeBudget {
59
+ remaining: number;
60
+ }
61
+
62
+ /**
63
+ * Recursively sum the byte size of every regular file under `absPath`,
64
+ * sharing a single entry budget across all directories in the same listing.
65
+ *
66
+ * Returns:
67
+ * - the total size in bytes when the entire subtree was traversed within
68
+ * budget
69
+ * - `null` if the shared budget was exhausted before completion (the caller
70
+ * surfaces that as an unknown size in the UI)
71
+ *
72
+ * Symlinks are not followed. We rely on `withFileTypes` so we never `stat`
73
+ * directories purely to discover their type.
74
+ */
75
+ function computeDirSize(absPath: string, budget: DirSizeBudget): number | null {
76
+ if (budget.remaining <= 0) return null;
77
+
78
+ let total = 0;
79
+ const stack: string[] = [absPath];
80
+
81
+ while (stack.length > 0) {
82
+ const dir = stack.pop()!;
83
+
84
+ let dirents: Dirent[];
85
+ try {
86
+ dirents = readdirSync(dir, { withFileTypes: true });
87
+ } catch {
88
+ continue;
89
+ }
90
+
91
+ for (const entry of dirents) {
92
+ if (budget.remaining <= 0) return null;
93
+ budget.remaining -= 1;
94
+
95
+ if (entry.isDirectory()) {
96
+ stack.push(join(dir, entry.name));
97
+ } else if (entry.isFile()) {
98
+ try {
99
+ total += statSync(join(dir, entry.name)).size;
100
+ } catch {
101
+ // unreadable file — skip, do not abort the whole computation
102
+ }
103
+ }
104
+ // symlinks, sockets, fifos, etc. are intentionally ignored
105
+ }
106
+ }
107
+
108
+ return total;
43
109
  }
44
110
 
45
111
  const SOUNDS_WORKSPACE_PATH = "data/sounds";
@@ -75,6 +141,7 @@ function publishSoundsConfigUpdatedForPaths(
75
141
  function handleWorkspaceTree({ queryParams }: RouteHandlerArgs) {
76
142
  const requestedPath = queryParams?.path ?? "";
77
143
  const showHidden = queryParams?.showHidden === "true";
144
+ const includeDirSizes = queryParams?.includeDirSizes === "true";
78
145
  const resolved = resolveWorkspacePath(requestedPath, {
79
146
  allowHidden: showHidden,
80
147
  });
@@ -86,6 +153,12 @@ function handleWorkspaceTree({ queryParams }: RouteHandlerArgs) {
86
153
  const dirents = readdirSync(resolved, { withFileTypes: true });
87
154
  const workspaceDir = getWorkspaceDir();
88
155
 
156
+ // Shared budget across every directory in this listing. When opted out,
157
+ // we never construct one, so directories report `size: null` as before.
158
+ const dirSizeBudget: DirSizeBudget | undefined = includeDirSizes
159
+ ? { remaining: DIR_SIZE_TOTAL_ENTRY_BUDGET }
160
+ : undefined;
161
+
89
162
  const entries: TreeEntry[] = [];
90
163
  for (const entry of dirents) {
91
164
  if (!showHidden && entry.name.startsWith(".")) continue;
@@ -102,11 +175,14 @@ function handleWorkspaceTree({ queryParams }: RouteHandlerArgs) {
102
175
  const isDir = stats.isDirectory();
103
176
  const relativePath = fullPath.slice(workspaceDir.length + 1);
104
177
 
178
+ const dirSize =
179
+ isDir && dirSizeBudget ? computeDirSize(fullPath, dirSizeBudget) : null;
180
+
105
181
  entries.push({
106
182
  name: entry.name,
107
183
  path: relativePath,
108
184
  type: isDir ? "directory" : "file",
109
- size: isDir ? null : stats.size,
185
+ size: isDir ? dirSize : stats.size,
110
186
  mimeType: isDir ? null : Bun.file(fullPath).type,
111
187
  modifiedAt: stats.mtime.toISOString(),
112
188
  });
@@ -416,6 +492,10 @@ export const ROUTES: RouteDefinition[] = [
416
492
  operationId: "workspace_tree",
417
493
  endpoint: "workspace/tree",
418
494
  method: "GET",
495
+ policy: {
496
+ requiredScopes: ["settings.read"],
497
+ allowedPrincipalTypes: ACTOR_PRINCIPALS,
498
+ },
419
499
  summary: "List workspace directory",
420
500
  description: "Return directory entries for a workspace path.",
421
501
  tags: ["workspace"],
@@ -428,10 +508,17 @@ export const ROUTES: RouteDefinition[] = [
428
508
  name: "showHidden",
429
509
  description: "Include dotfiles (true/false)",
430
510
  },
511
+ {
512
+ name: "includeDirSizes",
513
+ description:
514
+ "Compute recursive byte size for each directory entry (true/false). Budget-bounded — large subtrees may return size: null.",
515
+ },
431
516
  ],
432
517
  responseBody: z.object({
433
518
  path: z.string(),
434
- entries: z.array(z.unknown()).describe("Directory entry objects"),
519
+ entries: z
520
+ .array(workspaceTreeEntrySchema)
521
+ .describe("Directory entry objects"),
435
522
  }),
436
523
  handler: handleWorkspaceTree,
437
524
  },
@@ -439,6 +526,10 @@ export const ROUTES: RouteDefinition[] = [
439
526
  operationId: "workspace_file",
440
527
  endpoint: "workspace/file",
441
528
  method: "GET",
529
+ policy: {
530
+ requiredScopes: ["settings.read"],
531
+ allowedPrincipalTypes: ACTOR_PRINCIPALS,
532
+ },
442
533
  summary: "Get workspace file metadata",
443
534
  description:
444
535
  "Return file metadata and inline text content (if small enough).",
@@ -468,6 +559,10 @@ export const ROUTES: RouteDefinition[] = [
468
559
  operationId: "workspace_write",
469
560
  endpoint: "workspace/write",
470
561
  method: "POST",
562
+ policy: {
563
+ requiredScopes: ["settings.write"],
564
+ allowedPrincipalTypes: ACTOR_PRINCIPALS,
565
+ },
471
566
  summary: "Write workspace file",
472
567
  description: "Create or overwrite a file in the workspace.",
473
568
  tags: ["workspace"],
@@ -489,6 +584,10 @@ export const ROUTES: RouteDefinition[] = [
489
584
  operationId: "workspace_mkdir",
490
585
  endpoint: "workspace/mkdir",
491
586
  method: "POST",
587
+ policy: {
588
+ requiredScopes: ["settings.write"],
589
+ allowedPrincipalTypes: ACTOR_PRINCIPALS,
590
+ },
492
591
  summary: "Create workspace directory",
493
592
  description: "Create directories recursively in the workspace.",
494
593
  tags: ["workspace"],
@@ -504,6 +603,10 @@ export const ROUTES: RouteDefinition[] = [
504
603
  operationId: "workspace_rename",
505
604
  endpoint: "workspace/rename",
506
605
  method: "POST",
606
+ policy: {
607
+ requiredScopes: ["settings.write"],
608
+ allowedPrincipalTypes: ACTOR_PRINCIPALS,
609
+ },
507
610
  summary: "Rename workspace entry",
508
611
  description: "Rename or move a file or directory in the workspace.",
509
612
  tags: ["workspace"],
@@ -521,6 +624,10 @@ export const ROUTES: RouteDefinition[] = [
521
624
  operationId: "workspace_delete",
522
625
  endpoint: "workspace/delete",
523
626
  method: "POST",
627
+ policy: {
628
+ requiredScopes: ["settings.write"],
629
+ allowedPrincipalTypes: ACTOR_PRINCIPALS,
630
+ },
524
631
  summary: "Delete workspace entry",
525
632
  description: "Delete a file or directory from the workspace.",
526
633
  tags: ["workspace"],
@@ -536,6 +643,10 @@ export const ROUTES: RouteDefinition[] = [
536
643
  operationId: "workspace_file_content",
537
644
  endpoint: "workspace/file/content",
538
645
  method: "GET",
646
+ policy: {
647
+ requiredScopes: ["settings.read"],
648
+ allowedPrincipalTypes: ACTOR_PRINCIPALS,
649
+ },
539
650
  summary: "Get workspace file content",
540
651
  description: "Return raw file bytes with HTTP range support.",
541
652
  tags: ["workspace"],
@@ -167,7 +167,7 @@ describe("analyzeConversation", () => {
167
167
  "analysis-new",
168
168
  "user",
169
169
  expect.any(String),
170
- { provenanceTrustClass: "unknown" },
170
+ { metadata: { provenanceTrustClass: "unknown" } },
171
171
  );
172
172
 
173
173
  // Sets trust context to unknown.
@@ -192,7 +192,6 @@ describe("analyzeConversation", () => {
192
192
  expect(currentConversation.runAgentLoop).toHaveBeenCalledWith(
193
193
  expect.any(String),
194
194
  "msg-1",
195
- undefined,
196
195
  expect.objectContaining({
197
196
  isInteractive: false,
198
197
  isUserMessage: true,
@@ -287,7 +286,7 @@ describe("analyzeConversation", () => {
287
286
  "analysis-existing",
288
287
  "user",
289
288
  expect.any(String),
290
- { provenanceTrustClass: "guardian" },
289
+ { metadata: { provenanceTrustClass: "guardian" } },
291
290
  );
292
291
  });
293
292
 
@@ -366,7 +365,6 @@ describe("analyzeConversation", () => {
366
365
  expect(currentConversation.runAgentLoop).toHaveBeenCalledWith(
367
366
  expect.any(String),
368
367
  "msg-1",
369
- undefined,
370
368
  expect.objectContaining({ callSite: "analyzeConversation" }),
371
369
  );
372
370
  });
@@ -35,10 +35,7 @@ import {
35
35
  } from "../../memory/conversation-crud.js";
36
36
  import { resolveConversationId } from "../../memory/conversation-key-store.js";
37
37
  import { getLogger } from "../../util/logger.js";
38
- import {
39
- assistantEventHub,
40
- broadcastMessage,
41
- } from "../assistant-event-hub.js";
38
+ import { assistantEventHub, broadcastMessage } from "../assistant-event-hub.js";
42
39
  import {
43
40
  buildAutoAnalysisPrompt,
44
41
  neutralizeTranscriptSentinel,
@@ -218,7 +215,7 @@ export async function analyzeConversation(
218
215
  analysisConversationId,
219
216
  "user",
220
217
  JSON.stringify([{ type: "text", text: prompt }]),
221
- { provenanceTrustClass: trustClass },
218
+ { metadata: { provenanceTrustClass: trustClass } },
222
219
  );
223
220
  const messageId = message.id;
224
221
 
@@ -258,7 +255,7 @@ export async function analyzeConversation(
258
255
  // routes the per-call provider config through `resolveCallSiteConfig`
259
256
  // against `llm.callSites.analyzeConversation`.
260
257
  analysisConversation
261
- .runAgentLoop(prompt, messageId, undefined, {
258
+ .runAgentLoop(prompt, messageId, {
262
259
  isInteractive: false,
263
260
  isUserMessage: true,
264
261
  callSite: "analyzeConversation",
@@ -9,6 +9,7 @@
9
9
 
10
10
  import { parseChannelId } from "../../channels/types.js";
11
11
  import { getConfig } from "../../config/loader.js";
12
+ import { findConversation } from "../../daemon/conversation-store.js";
12
13
  import { normalizeConversationType } from "../../daemon/message-types/shared.js";
13
14
  import {
14
15
  type AttentionState,
@@ -162,9 +163,24 @@ export function serializeConversationSummary(params: {
162
163
  groupId: string | null;
163
164
  };
164
165
  parentCache: Map<string, ConversationRow | null>;
166
+ /**
167
+ * Whether the agent loop is currently mid-turn for this conversation.
168
+ * Sourced from the in-memory daemon `Conversation.isProcessing()` flag
169
+ * — callers resolve via `findConversation(id)?.isProcessing() ?? false`
170
+ * so cold (evicted / never-loaded) rows report `false`. Plumbed in
171
+ * rather than read here so the serializer stays a pure shape mapper
172
+ * with no daemon-store coupling.
173
+ */
174
+ isProcessing: boolean;
165
175
  }) {
166
- const { conversation, binding, attentionState, displayMeta, parentCache } =
167
- params;
176
+ const {
177
+ conversation,
178
+ binding,
179
+ attentionState,
180
+ displayMeta,
181
+ parentCache,
182
+ isProcessing,
183
+ } = params;
168
184
  const originChannel = parseChannelId(conversation.originChannel);
169
185
  const assistantAttention = buildAssistantAttention(attentionState);
170
186
  const forkParent = buildForkParent(conversation, parentCache);
@@ -205,6 +221,7 @@ export function serializeConversationSummary(params: {
205
221
  ...(conversation.inferenceProfile != null
206
222
  ? { inferenceProfile: conversation.inferenceProfile }
207
223
  : {}),
224
+ isProcessing,
208
225
  };
209
226
  }
210
227
 
@@ -232,6 +249,11 @@ export function buildConversationDetailResponse(
232
249
  attentionState: attentionStates.get(conversation.id),
233
250
  displayMeta: displayMeta.get(conversation.id),
234
251
  parentCache,
252
+ // Cold (evicted / never-loaded) rows aren't in the in-memory
253
+ // store, so `findConversation` returns `undefined` and they
254
+ // report `isProcessing: false` — by definition they aren't
255
+ // mid-turn since the agent loop only runs on resident convs.
256
+ isProcessing: findConversation(conversation.id)?.isProcessing() ?? false,
235
257
  }),
236
258
  };
237
259
  }
@@ -1,5 +1,5 @@
1
+ import type { ConversationListInvalidatedReason } from "../../api/events/conversation-list-invalidated.js";
1
2
  import type { IdentityFields } from "../../daemon/handlers/identity.js";
2
- import type { ConversationListInvalidatedReason } from "../../daemon/message-types/conversations.js";
3
3
  import {
4
4
  conversationMessagesSyncTag,
5
5
  conversationMetadataSyncTag,
@@ -29,7 +29,17 @@ export function publishIdentityChanged(
29
29
  emoji: fields.emoji,
30
30
  home: fields.home,
31
31
  });
32
- void publishSyncInvalidation([SYNC_TAGS.assistantIdentity], originClientId);
32
+ void publishSyncInvalidation(
33
+ [SYNC_TAGS.assistantIdentity, SYNC_TAGS.assistantIdentityIntro],
34
+ originClientId,
35
+ );
36
+ }
37
+
38
+ export function publishIdentityIntroChanged(originClientId?: string): void {
39
+ void publishSyncInvalidation(
40
+ [SYNC_TAGS.assistantIdentityIntro],
41
+ originClientId,
42
+ );
33
43
  }
34
44
 
35
45
  export function publishConfigChanged(originClientId?: string): void {
@@ -46,6 +56,10 @@ export function publishSchedulesChanged(originClientId?: string): void {
46
56
  void publishSyncInvalidation([SYNC_TAGS.assistantSchedules], originClientId);
47
57
  }
48
58
 
59
+ export function publishAppsChanged(originClientId?: string): void {
60
+ void publishSyncInvalidation([SYNC_TAGS.appsList], originClientId);
61
+ }
62
+
49
63
  /**
50
64
  * Reasons that change the *shape* of the conversation list — a row is
51
65
  * added, removed, or its position changes. These require web clients to
@@ -1,6 +1,6 @@
1
- import type { SyncChangedMessage } from "../../daemon/message-types/sync.js";
2
1
  import {
3
2
  buildSyncChangedMessage,
3
+ type SyncChangedEvent,
4
4
  type SyncInvalidationTag,
5
5
  } from "../../daemon/message-types/sync.js";
6
6
  import { getLogger } from "../../util/logger.js";
@@ -11,7 +11,7 @@ const log = getLogger("sync-publisher");
11
11
  export async function publishSyncInvalidation(
12
12
  tags: SyncInvalidationTag[],
13
13
  originClientId?: string,
14
- ): Promise<SyncChangedMessage> {
14
+ ): Promise<SyncChangedEvent> {
15
15
  const message = buildSyncChangedMessage(tags, originClientId);
16
16
  try {
17
17
  broadcastMessage(message);
@@ -6,8 +6,16 @@ const log = getLogger("run-script");
6
6
 
7
7
  /** Maximum combined stdout + stderr captured (bytes). */
8
8
  const MAX_OUTPUT_BYTES = 10_000;
9
- /** Default timeout for script execution (ms). */
10
- const DEFAULT_TIMEOUT_MS = 60_000;
9
+ /** Default timeout for script execution (ms) when a schedule sets no override. */
10
+ export const DEFAULT_TIMEOUT_MS = 60_000;
11
+ /** Smallest script timeout override a caller may set (ms). */
12
+ export const MIN_SCRIPT_TIMEOUT_MS = 1_000;
13
+ /**
14
+ * Largest script timeout override a caller may set (ms). Capped so a wedged
15
+ * script cannot block the scheduler tick indefinitely; mirrors the talk-mode
16
+ * budget in scheduler.ts.
17
+ */
18
+ export const MAX_SCRIPT_TIMEOUT_MS = 30 * 60 * 1000;
11
19
 
12
20
  export interface ScriptResult {
13
21
  exitCode: number;
@@ -75,7 +83,9 @@ export async function runScript(
75
83
  ]);
76
84
  const stdout = truncate(stdoutStr);
77
85
  const timeoutMsg = `Script timed out after ${timeoutMs}ms`;
78
- const stderr = truncate(stderrStr ? `${timeoutMsg}\n${stderrStr}` : timeoutMsg);
86
+ const stderr = truncate(
87
+ stderrStr ? `${timeoutMsg}\n${stderrStr}` : timeoutMsg,
88
+ );
79
89
  log.info(
80
90
  { command, timedOut: true, stdoutLen: stdout.length },
81
91
  "Script timed out",
@@ -98,3 +108,18 @@ function truncate(text: string): string {
98
108
  if (text.length <= MAX_OUTPUT_BYTES) return text;
99
109
  return text.slice(0, MAX_OUTPUT_BYTES) + "\n... (truncated)";
100
110
  }
111
+
112
+ /**
113
+ * Validate a caller-supplied script timeout override (ms). Returns an error
114
+ * message when the value is not a positive integer within the allowed bounds,
115
+ * or `null` when it is acceptable.
116
+ */
117
+ export function validateScriptTimeoutMs(value: number): string | null {
118
+ if (!Number.isInteger(value)) {
119
+ return "timeout_ms must be an integer number of milliseconds";
120
+ }
121
+ if (value < MIN_SCRIPT_TIMEOUT_MS || value > MAX_SCRIPT_TIMEOUT_MS) {
122
+ return `timeout_ms must be between ${MIN_SCRIPT_TIMEOUT_MS} and ${MAX_SCRIPT_TIMEOUT_MS} (ms)`;
123
+ }
124
+ return null;
125
+ }
@@ -47,6 +47,8 @@ export interface ScheduleJob {
47
47
  retryCount: number;
48
48
  maxRetries: number;
49
49
  retryBackoffMs: number;
50
+ /** Script-mode execution timeout override (ms); null = use the default. */
51
+ timeoutMs: number | null;
50
52
  createdBy: string;
51
53
  mode: ScheduleMode;
52
54
  routingIntent: RoutingIntent;
@@ -99,6 +101,7 @@ export function createSchedule(params: {
99
101
  reuseConversation?: boolean;
100
102
  maxRetries?: number;
101
103
  retryBackoffMs?: number;
104
+ timeoutMs?: number | null;
102
105
  }): ScheduleJob {
103
106
  const expression = params.expression ?? params.cronExpression ?? null;
104
107
  const isOneShot = expression == null;
@@ -134,6 +137,7 @@ export function createSchedule(params: {
134
137
  const reuseConversation = params.reuseConversation ?? !isOneShot;
135
138
  const maxRetries = params.maxRetries ?? 3;
136
139
  const retryBackoffMs = params.retryBackoffMs ?? 60000;
140
+ const timeoutMs = params.timeoutMs ?? null;
137
141
 
138
142
  let nextRunAt: number;
139
143
  if (isOneShot) {
@@ -160,6 +164,7 @@ export function createSchedule(params: {
160
164
  retryCount: 0,
161
165
  maxRetries,
162
166
  retryBackoffMs,
167
+ timeoutMs,
163
168
  createdBy: params.createdBy ?? "agent",
164
169
  mode,
165
170
  routingIntent,
@@ -258,6 +263,7 @@ export function updateSchedule(
258
263
  wakeConversationId?: string | null;
259
264
  maxRetries?: number;
260
265
  retryBackoffMs?: number;
266
+ timeoutMs?: number | null;
261
267
  },
262
268
  ): ScheduleJob | null {
263
269
  const db = getDb();
@@ -322,6 +328,7 @@ export function updateSchedule(
322
328
  if (updates.maxRetries !== undefined) set.maxRetries = updates.maxRetries;
323
329
  if (updates.retryBackoffMs !== undefined)
324
330
  set.retryBackoffMs = updates.retryBackoffMs;
331
+ if (updates.timeoutMs !== undefined) set.timeoutMs = updates.timeoutMs;
325
332
 
326
333
  // Recompute nextRunAt if schedule timing may have changed (only for recurring)
327
334
  if (
@@ -969,6 +976,7 @@ function parseJobRow(row: typeof scheduleJobs.$inferSelect): ScheduleJob {
969
976
  retryCount: row.retryCount,
970
977
  maxRetries: row.maxRetries ?? 3,
971
978
  retryBackoffMs: row.retryBackoffMs ?? 60000,
979
+ timeoutMs: row.timeoutMs ?? null,
972
980
  createdBy: row.createdBy,
973
981
  mode: (row.mode ?? "execute") as ScheduleMode,
974
982
  routingIntent: (row.routingIntent ?? "all_channels") as RoutingIntent,
@@ -303,7 +303,9 @@ export async function runScheduleDueWorkOnce(
303
303
  { jobId: job.id, name: job.name, isOneShot },
304
304
  "Executing script schedule",
305
305
  );
306
- const result: ScriptResult = await runScript(job.script);
306
+ const result: ScriptResult = await runScript(job.script, {
307
+ timeoutMs: job.timeoutMs ?? undefined,
308
+ });
307
309
  completeScheduleRun(runId, {
308
310
  status: result.exitCode === 0 ? "ok" : "error",
309
311
  output: result.stdout || undefined,
@@ -134,14 +134,11 @@ async function dispatchUserMessage(params: {
134
134
  return { accepted: !result.rejected };
135
135
  }
136
136
 
137
- await processMessageInBackground(
138
- conversationId,
139
- params.content,
140
- attachmentIds.length > 0 ? attachmentIds : undefined,
141
- undefined,
142
- params.sourceChannel,
143
- params.sourceInterface,
144
- );
137
+ await processMessageInBackground(conversationId, params.content, {
138
+ attachmentIds: attachmentIds.length > 0 ? attachmentIds : undefined,
139
+ sourceChannel: params.sourceChannel,
140
+ sourceInterface: params.sourceInterface,
141
+ });
145
142
  return { accepted: true };
146
143
  }
147
144
 
@@ -37,6 +37,7 @@ import {
37
37
  import { getLogger } from "../util/logger.js";
38
38
  import { getCachedCatalogSync, getCatalog } from "./catalog-cache.js";
39
39
  import { type CatalogSkill, getRepoSkillsDir } from "./catalog-install.js";
40
+ import { inferCategory } from "./category-inference.js";
40
41
  import type { SkillFileProvider } from "./skill-file-provider.js";
41
42
 
42
43
  const log = getLogger("catalog-files");
@@ -497,14 +498,16 @@ export async function readCatalogSkillFileContent(
497
498
  * otherwise be reachable via the handler module.
498
499
  */
499
500
  export function catalogSkillToSlim(cs: CatalogSkill): SlimSkillResponse {
501
+ const name = cs.metadata?.vellum?.["display-name"] ?? cs.name;
500
502
  return {
501
503
  id: cs.id,
502
- name: cs.metadata?.vellum?.["display-name"] ?? cs.name,
504
+ name,
503
505
  description: cs.description,
504
506
  emoji: cs.emoji ?? cs.metadata?.emoji,
505
507
  kind: "catalog",
506
508
  origin: "vellum",
507
509
  status: "available",
510
+ category: inferCategory(name, cs.description),
508
511
  };
509
512
  }
510
513
 
@@ -17,6 +17,7 @@ import type { SlimSkillResponse } from "../daemon/message-types/skills.js";
17
17
  import { isTextMimeType as isTextMime } from "../runtime/routes/workspace-utils.js";
18
18
  import { getLogger } from "../util/logger.js";
19
19
  import type { SkillFileEntry } from "./catalog-files.js";
20
+ import { inferCategory } from "./category-inference.js";
20
21
  import {
21
22
  clawhubInspect,
22
23
  clawhubInspectFile,
@@ -198,6 +199,7 @@ export function createClawhubProvider(): SkillFileProvider {
198
199
  kind: "catalog",
199
200
  status: "available",
200
201
  origin: "clawhub",
202
+ category: inferCategory(data.skill.displayName, data.skill.summary),
201
203
  slug: data.skill.slug,
202
204
  author: data.owner?.handle ?? "",
203
205
  stars: data.stats?.stars ?? 0,
@@ -24,6 +24,7 @@ import {
24
24
  sanitizeRelativePath,
25
25
  SKIP_DIRS,
26
26
  } from "./catalog-files.js";
27
+ import { inferCategory } from "./category-inference.js";
27
28
  import type { SkillFileProvider } from "./skill-file-provider.js";
28
29
  import type { GitHubContentsEntry } from "./skillssh-registry.js";
29
30
  import {
@@ -383,6 +384,7 @@ export function createSkillsShProvider(): SkillFileProvider {
383
384
  kind: "catalog",
384
385
  status: "available",
385
386
  origin: "skillssh",
387
+ category: inferCategory(source.skillSlug, ""),
386
388
  slug: skillId,
387
389
  sourceRepo: `${source.owner}/${source.repo}`,
388
390
  installs: 0,
@@ -285,12 +285,9 @@ export class SubagentManager {
285
285
  conversationRecord.id,
286
286
  provider,
287
287
  systemPrompt,
288
- maxTokens,
289
288
  wrappedSendToClient,
290
289
  workingDir,
291
- undefined, // sharedCesClient
292
- undefined, // speedOverride
293
- "5m", // cacheTtl — subagents run tight tool-use loops, 5m is always hot
290
+ { maxTokens, cacheTtl: "5m" },
294
291
  );
295
292
 
296
293
  // Mark conversation as having no direct client — it routes through parent.
@@ -439,7 +436,7 @@ export class SubagentManager {
439
436
  const { id: messageId } = await conversation.persistUserMessage({
440
437
  content: message,
441
438
  });
442
- await conversation.runAgentLoop(message, messageId, undefined, {
439
+ await conversation.runAgentLoop(message, messageId, {
443
440
  callSite: "subagentSpawn",
444
441
  ...(managed.state.config.overrideProfile
445
442
  ? { overrideProfile: managed.state.config.overrideProfile }
@@ -627,7 +624,7 @@ export class SubagentManager {
627
624
  content: trimmed,
628
625
  });
629
626
  conversation
630
- .runAgentLoop(trimmed, messageId, undefined, {
627
+ .runAgentLoop(trimmed, messageId, {
631
628
  callSite: "subagentSpawn",
632
629
  ...(managed.state.config.overrideProfile
633
630
  ? { overrideProfile: managed.state.config.overrideProfile }
@@ -6,6 +6,32 @@ export interface TelemetryEventBase {
6
6
  type: string;
7
7
  daemon_event_id: string;
8
8
  recorded_at: number;
9
+ /**
10
+ * Version of the assistant binary at the moment THIS event was
11
+ * RECORDED (not when the batch was uploaded). Distinct from the
12
+ * envelope's `assistant_version` field, which still ships for
13
+ * back-compat with platforms that haven't deployed the per-event
14
+ * handling.
15
+ *
16
+ * The platform's `TelemetryIngestView` prefers per-event over
17
+ * envelope: when a per-event value is present (including explicit
18
+ * `null`) it wins. When the field is omitted on the event entirely
19
+ * (old assistant), the envelope value is the back-compat fallback.
20
+ *
21
+ * Daemon-side, this field is always non-null — the reporter stamps
22
+ * the running binary's `APP_VERSION` when the underlying SQLite row
23
+ * has no record-time value. In this PR only `llm_usage` events
24
+ * carry a true record-time value (legacy llm_usage rows from before
25
+ * migration 267 fall back to `APP_VERSION`); turn, lifecycle, and
26
+ * onboarding events all stamp `APP_VERSION` directly until the
27
+ * follow-ups that add the column to `messages` / `lifecycle_events`
28
+ * (#18112) / `onboarding_events` (#30733) land. Stamping
29
+ * `APP_VERSION` instead of emitting explicit `null` preserves
30
+ * envelope-equivalent behavior under the per-event-wins contract.
31
+ * The type allows `null` for parity with the platform contract;
32
+ * in practice the daemon never sends it.
33
+ */
34
+ assistant_version: string | null;
9
35
  }
10
36
 
11
37
  /** LLM usage event — one per provider API call. */