@vellumai/assistant 0.5.16 → 0.6.0

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 (407) hide show
  1. package/ARCHITECTURE.md +1 -1
  2. package/Dockerfile +0 -3
  3. package/knip.json +2 -1
  4. package/openapi.yaml +660 -80
  5. package/package.json +1 -1
  6. package/src/__tests__/actor-token-service.test.ts +68 -0
  7. package/src/__tests__/agent-loop.test.ts +0 -32
  8. package/src/__tests__/always-loaded-tools-guard.test.ts +2 -2
  9. package/src/__tests__/anthropic-provider.test.ts +57 -3
  10. package/src/__tests__/app-compiler.test.ts +120 -0
  11. package/src/__tests__/assistant-feature-flags-integration.test.ts +2 -2
  12. package/src/__tests__/call-conversation-messages.test.ts +2 -6
  13. package/src/__tests__/call-domain.test.ts +2 -6
  14. package/src/__tests__/call-pointer-messages.test.ts +2 -14
  15. package/src/__tests__/call-recovery.test.ts +2 -6
  16. package/src/__tests__/call-routes-http.test.ts +2 -6
  17. package/src/__tests__/call-store.test.ts +2 -6
  18. package/src/__tests__/cancel-resolves-conversation-key.test.ts +2 -6
  19. package/src/__tests__/canonical-guardian-store.test.ts +2 -6
  20. package/src/__tests__/channel-delivery-store.test.ts +2 -6
  21. package/src/__tests__/channel-retry-sweep.test.ts +2 -6
  22. package/src/__tests__/checker.test.ts +25 -3
  23. package/src/__tests__/clawhub.test.ts +54 -24
  24. package/src/__tests__/cli-command-risk-guard.test.ts +14 -0
  25. package/src/__tests__/cli-memory.test.ts +74 -69
  26. package/src/__tests__/config-schema.test.ts +1 -1
  27. package/src/__tests__/config-set-platform-guard.test.ts +302 -0
  28. package/src/__tests__/confirmation-request-guardian-bridge.test.ts +2 -6
  29. package/src/__tests__/contacts-tools.test.ts +31 -0
  30. package/src/__tests__/context-overflow-reducer.test.ts +86 -0
  31. package/src/__tests__/context-token-estimator.test.ts +175 -10
  32. package/src/__tests__/conversation-agent-loop-overflow.test.ts +9 -0
  33. package/src/__tests__/conversation-agent-loop.test.ts +9 -0
  34. package/src/__tests__/conversation-attachments.test.ts +2 -6
  35. package/src/__tests__/conversation-attention-store.test.ts +2 -6
  36. package/src/__tests__/conversation-clear-safety.test.ts +2 -6
  37. package/src/__tests__/conversation-delete-schedule-cleanup.test.ts +4 -10
  38. package/src/__tests__/conversation-disk-view-integration.test.ts +2 -6
  39. package/src/__tests__/conversation-disk-view.test.ts +2 -6
  40. package/src/__tests__/conversation-error.test.ts +33 -2
  41. package/src/__tests__/conversation-fork-crud.test.ts +2 -6
  42. package/src/__tests__/conversation-history-web-search.test.ts +5 -0
  43. package/src/__tests__/conversation-load-history-repair.test.ts +5 -1
  44. package/src/__tests__/conversation-media-retry.test.ts +91 -0
  45. package/src/__tests__/conversation-starter-routes.test.ts +20 -11
  46. package/src/__tests__/conversation-store.test.ts +2 -6
  47. package/src/__tests__/conversation-usage.test.ts +2 -6
  48. package/src/__tests__/conversation-wipe.test.ts +11 -408
  49. package/src/__tests__/credential-execution-feature-gates.test.ts +3 -3
  50. package/src/__tests__/credential-execution-shell-lockdown.test.ts +2 -2
  51. package/src/__tests__/credential-security-e2e.test.ts +2 -0
  52. package/src/__tests__/followup-tools.test.ts +2 -6
  53. package/src/__tests__/graph-extraction-event-date.test.ts +186 -0
  54. package/src/__tests__/guardian-action-conversation-turn.test.ts +2 -6
  55. package/src/__tests__/guardian-action-followup-executor.test.ts +2 -6
  56. package/src/__tests__/guardian-action-followup-store.test.ts +2 -6
  57. package/src/__tests__/guardian-action-grant-mint-consume.test.ts +2 -6
  58. package/src/__tests__/guardian-action-late-reply.test.ts +2 -6
  59. package/src/__tests__/guardian-action-store.test.ts +2 -6
  60. package/src/__tests__/guardian-binding-drift-heal.test.ts +2 -6
  61. package/src/__tests__/guardian-decision-primitive-canonical.test.ts +8 -8
  62. package/src/__tests__/guardian-dispatch.test.ts +2 -6
  63. package/src/__tests__/guardian-grant-minting.test.ts +2 -14
  64. package/src/__tests__/guardian-principal-id-roundtrip.test.ts +2 -6
  65. package/src/__tests__/guardian-routing-invariants.test.ts +192 -6
  66. package/src/__tests__/guardian-routing-state.test.ts +2 -6
  67. package/src/__tests__/guardian-verification-voice-binding.test.ts +2 -6
  68. package/src/__tests__/inbound-invite-redemption.test.ts +2 -6
  69. package/src/__tests__/injection-block.test.ts +154 -0
  70. package/src/__tests__/install-meta.test.ts +506 -0
  71. package/src/__tests__/install-skill-routing.test.ts +292 -0
  72. package/src/__tests__/invite-redemption-service.test.ts +2 -6
  73. package/src/__tests__/invite-routes-http.test.ts +2 -6
  74. package/src/__tests__/jobs-store-qdrant-breaker.test.ts +2 -14
  75. package/src/__tests__/list-messages-attachments.test.ts +2 -6
  76. package/src/__tests__/llm-context-route-provider.test.ts +2 -6
  77. package/src/__tests__/llm-request-log-turn-query.test.ts +2 -6
  78. package/src/__tests__/llm-usage-store.test.ts +2 -6
  79. package/src/__tests__/log-export-workspace.test.ts +2 -6
  80. package/src/__tests__/managed-store.test.ts +38 -11
  81. package/src/__tests__/memory-jobs-worker-backoff.test.ts +2 -8
  82. package/src/__tests__/memory-recall-log-store.test.ts +2 -6
  83. package/src/__tests__/memory-upsert-concurrency.test.ts +4 -112
  84. package/src/__tests__/non-member-access-request.test.ts +2 -6
  85. package/src/__tests__/notification-guardian-path.test.ts +2 -6
  86. package/src/__tests__/oauth-cli.test.ts +364 -2
  87. package/src/__tests__/oauth2-gateway-transport.test.ts +18 -3
  88. package/src/__tests__/outlook-attachments.test.ts +301 -0
  89. package/src/__tests__/outlook-automation-tools.test.ts +425 -0
  90. package/src/__tests__/outlook-categories.test.ts +212 -0
  91. package/src/__tests__/outlook-client-automation.test.ts +246 -0
  92. package/src/__tests__/outlook-compose-tools.test.ts +325 -0
  93. package/src/__tests__/outlook-declutter-tools.test.ts +585 -0
  94. package/src/__tests__/outlook-email-watcher.test.ts +322 -0
  95. package/src/__tests__/outlook-follow-up.test.ts +196 -0
  96. package/src/__tests__/outlook-messaging-provider.test.ts +498 -3
  97. package/src/__tests__/outlook-trash.test.ts +77 -0
  98. package/src/__tests__/outlook-unsubscribe.test.ts +250 -0
  99. package/src/__tests__/platform-callback-registration.test.ts +4 -4
  100. package/src/__tests__/playbook-execution.test.ts +76 -80
  101. package/src/__tests__/playbook-tools.test.ts +5 -7
  102. package/src/__tests__/provider-error-scenarios.test.ts +21 -0
  103. package/src/__tests__/rebuild-index-graph-nodes.test.ts +273 -0
  104. package/src/__tests__/registry.test.ts +2 -2
  105. package/src/__tests__/require-fresh-approval.test.ts +64 -2
  106. package/src/__tests__/runtime-events-sse-parity.test.ts +2 -6
  107. package/src/__tests__/runtime-events-sse.test.ts +2 -6
  108. package/src/__tests__/schedule-store.test.ts +2 -6
  109. package/src/__tests__/schedule-tools.test.ts +2 -6
  110. package/src/__tests__/scheduler-recurrence.test.ts +1 -5
  111. package/src/__tests__/scoped-approval-grants.test.ts +2 -6
  112. package/src/__tests__/scoped-grant-security-matrix.test.ts +2 -6
  113. package/src/__tests__/search-skills-unified.test.ts +421 -0
  114. package/src/__tests__/secret-onetime-send.test.ts +2 -0
  115. package/src/__tests__/send-endpoint-busy.test.ts +2 -6
  116. package/src/__tests__/sequence-store.test.ts +2 -6
  117. package/src/__tests__/server-history-render.test.ts +2 -6
  118. package/src/__tests__/skill-feature-flags-integration.test.ts +38 -31
  119. package/src/__tests__/skill-feature-flags.test.ts +6 -6
  120. package/src/__tests__/skill-load-feature-flag.test.ts +11 -11
  121. package/src/__tests__/skill-memory.test.ts +140 -98
  122. package/src/__tests__/skills-uninstall.test.ts +2 -2
  123. package/src/__tests__/skills.test.ts +1 -1
  124. package/src/__tests__/slack-inbound-verification.test.ts +2 -6
  125. package/src/__tests__/task-compiler.test.ts +2 -6
  126. package/src/__tests__/task-management-tools.test.ts +2 -6
  127. package/src/__tests__/task-memory-cleanup.test.ts +173 -229
  128. package/src/__tests__/task-runner.test.ts +2 -6
  129. package/src/__tests__/task-scheduler.test.ts +2 -6
  130. package/src/__tests__/test-preload.ts +3 -0
  131. package/src/__tests__/tool-approval-handler.test.ts +2 -6
  132. package/src/__tests__/tool-grant-request-escalation.test.ts +2 -6
  133. package/src/__tests__/tool-side-effects-slack-dm.test.ts +276 -0
  134. package/src/__tests__/trust-store.test.ts +1 -1
  135. package/src/__tests__/trusted-contact-inline-approval-integration.test.ts +2 -6
  136. package/src/__tests__/trusted-contact-lifecycle-notifications.test.ts +2 -6
  137. package/src/__tests__/trusted-contact-multichannel.test.ts +2 -6
  138. package/src/__tests__/trusted-contact-verification.test.ts +2 -6
  139. package/src/__tests__/turn-boundary-resolution.test.ts +2 -6
  140. package/src/__tests__/usage-cache-backfill-migration.test.ts +1 -6
  141. package/src/__tests__/usage-routes.test.ts +2 -6
  142. package/src/__tests__/verification-control-plane-policy.test.ts +0 -2
  143. package/src/__tests__/voice-invite-redemption.test.ts +2 -6
  144. package/src/__tests__/voice-scoped-grant-consumer.test.ts +2 -6
  145. package/src/__tests__/voice-session-bridge.test.ts +2 -6
  146. package/src/__tests__/volume-security-guard.test.ts +2 -0
  147. package/src/__tests__/workspace-lifecycle.test.ts +29 -1
  148. package/src/__tests__/workspace-migration-009-backfill-conversation-disk-view.test.ts +2 -6
  149. package/src/__tests__/workspace-migration-013-repair-conversation-disk-view.test.ts +2 -6
  150. package/src/__tests__/workspace-migration-026-backfill-install-meta.test.ts +558 -0
  151. package/src/__tests__/workspace-policy.test.ts +1 -1
  152. package/src/agent/attachments.ts +7 -2
  153. package/src/agent/image-optimize.ts +165 -0
  154. package/src/agent/loop.ts +1 -15
  155. package/src/bundler/app-compiler.ts +179 -2
  156. package/src/bundler/package-resolver.ts +3 -5
  157. package/src/cli/__tests__/notifications.test.ts +1 -2
  158. package/src/cli/cli-memory.ts +67 -64
  159. package/src/cli/commands/avatar.ts +3 -3
  160. package/src/cli/commands/config.ts +26 -13
  161. package/src/cli/commands/doctor.ts +2 -2
  162. package/src/cli/commands/memory.ts +41 -55
  163. package/src/cli/commands/oauth/__tests__/connect.test.ts +2 -2
  164. package/src/cli/commands/oauth/__tests__/disconnect.test.ts +2 -2
  165. package/src/cli/commands/oauth/__tests__/mode.test.ts +8 -1
  166. package/src/cli/commands/oauth/__tests__/status.test.ts +2 -2
  167. package/src/cli/commands/oauth/connect.ts +11 -6
  168. package/src/cli/commands/oauth/mode.ts +7 -0
  169. package/src/cli/commands/oauth/shared.ts +39 -3
  170. package/src/cli/commands/platform/__tests__/connect.test.ts +1 -1
  171. package/src/cli/commands/platform/__tests__/disconnect.test.ts +1 -1
  172. package/src/cli/commands/platform/__tests__/status.test.ts +5 -5
  173. package/src/cli/commands/platform/index.ts +16 -16
  174. package/src/cli/commands/skills.ts +88 -16
  175. package/src/cli/commands/trust.ts +2 -2
  176. package/src/cli/lib/daemon-credential-client.ts +2 -3
  177. package/src/config/bundled-skills/acp/TOOLS.json +1 -1
  178. package/src/config/bundled-skills/contacts/SKILL.md +0 -1
  179. package/src/config/bundled-skills/contacts/TOOLS.json +0 -8
  180. package/src/config/bundled-skills/contacts/tools/contact-upsert.ts +0 -4
  181. package/src/config/bundled-skills/gmail/SKILL.md +2 -10
  182. package/src/config/bundled-skills/google-calendar/SKILL.md +1 -9
  183. package/src/config/bundled-skills/messaging/SKILL.md +10 -18
  184. package/src/config/bundled-skills/messaging/tools/messaging-analyze-style.ts +40 -33
  185. package/src/config/bundled-skills/outlook/SKILL.md +189 -0
  186. package/src/config/bundled-skills/outlook/TOOLS.json +530 -0
  187. package/src/config/bundled-skills/outlook/tools/outlook-attachments.ts +85 -0
  188. package/src/config/bundled-skills/outlook/tools/outlook-categories.ts +77 -0
  189. package/src/config/bundled-skills/outlook/tools/outlook-draft.ts +84 -0
  190. package/src/config/bundled-skills/outlook/tools/outlook-follow-up.ts +94 -0
  191. package/src/config/bundled-skills/outlook/tools/outlook-forward.ts +49 -0
  192. package/src/config/bundled-skills/outlook/tools/outlook-outreach-scan.ts +237 -0
  193. package/src/config/bundled-skills/outlook/tools/outlook-rules.ts +161 -0
  194. package/src/config/bundled-skills/outlook/tools/outlook-send-draft.ts +32 -0
  195. package/src/config/bundled-skills/outlook/tools/outlook-sender-digest.ts +272 -0
  196. package/src/config/bundled-skills/outlook/tools/outlook-trash.ts +29 -0
  197. package/src/config/bundled-skills/outlook/tools/outlook-unsubscribe.ts +129 -0
  198. package/src/config/bundled-skills/outlook/tools/outlook-vacation.ts +87 -0
  199. package/src/config/bundled-skills/outlook/tools/shared.ts +20 -0
  200. package/src/config/bundled-skills/outlook-calendar/SKILL.md +51 -0
  201. package/src/config/bundled-skills/outlook-calendar/TOOLS.json +221 -0
  202. package/src/config/bundled-skills/outlook-calendar/calendar-client.ts +252 -0
  203. package/src/config/bundled-skills/outlook-calendar/tools/outlook-calendar-check-availability.ts +53 -0
  204. package/src/config/bundled-skills/outlook-calendar/tools/outlook-calendar-create-event.ts +74 -0
  205. package/src/config/bundled-skills/outlook-calendar/tools/outlook-calendar-get-event.ts +18 -0
  206. package/src/config/bundled-skills/outlook-calendar/tools/outlook-calendar-list-events.ts +46 -0
  207. package/src/config/bundled-skills/outlook-calendar/tools/outlook-calendar-rsvp.ts +36 -0
  208. package/src/config/bundled-skills/outlook-calendar/tools/shared.ts +17 -0
  209. package/src/config/bundled-skills/outlook-calendar/types.ts +120 -0
  210. package/src/config/bundled-skills/playbooks/tools/playbook-create.ts +47 -40
  211. package/src/config/bundled-skills/playbooks/tools/playbook-delete.ts +16 -29
  212. package/src/config/bundled-skills/playbooks/tools/playbook-list.ts +16 -18
  213. package/src/config/bundled-skills/playbooks/tools/playbook-update.ts +39 -47
  214. package/src/config/bundled-skills/slack/SKILL.md +1 -7
  215. package/src/config/bundled-tool-registry.ts +56 -4
  216. package/src/config/env-registry.ts +15 -8
  217. package/src/config/feature-flag-registry.json +21 -124
  218. package/src/config/schemas/platform.ts +8 -0
  219. package/src/config/schemas/timeouts.ts +1 -1
  220. package/src/config/skills.ts +18 -7
  221. package/src/context/token-estimator.ts +25 -18
  222. package/src/context/window-manager.ts +6 -2
  223. package/src/credential-execution/process-manager.ts +3 -1
  224. package/src/daemon/context-overflow-reducer.ts +46 -2
  225. package/src/daemon/conversation-agent-loop-handlers.ts +123 -82
  226. package/src/daemon/conversation-agent-loop.ts +96 -61
  227. package/src/daemon/conversation-error.ts +31 -8
  228. package/src/daemon/conversation-lifecycle.ts +33 -0
  229. package/src/daemon/conversation-media-retry.ts +85 -7
  230. package/src/daemon/conversation-notifiers.ts +4 -1
  231. package/src/daemon/conversation-runtime-assembly.ts +5 -0
  232. package/src/daemon/conversation.ts +41 -2
  233. package/src/daemon/daemon-control.ts +8 -2
  234. package/src/daemon/handlers/shared.ts +22 -12
  235. package/src/daemon/handlers/skills.ts +416 -202
  236. package/src/daemon/lifecycle.ts +40 -1
  237. package/src/daemon/main.ts +5 -1
  238. package/src/daemon/message-types/conversations.ts +4 -1
  239. package/src/daemon/message-types/messages.ts +3 -1
  240. package/src/daemon/message-types/skills.ts +97 -36
  241. package/src/daemon/providers-setup.ts +5 -0
  242. package/src/daemon/server.ts +11 -2
  243. package/src/daemon/tool-side-effects.ts +27 -5
  244. package/src/heartbeat/heartbeat-service.ts +1 -0
  245. package/src/hooks/cli.ts +2 -2
  246. package/src/hooks/runner.ts +15 -38
  247. package/src/inbound/platform-callback-registration.ts +14 -14
  248. package/src/memory/admin.ts +11 -45
  249. package/src/memory/conversation-bootstrap.ts +2 -0
  250. package/src/memory/conversation-crud.ts +242 -348
  251. package/src/memory/conversation-group-migration.ts +157 -0
  252. package/src/memory/conversation-queries.ts +4 -2
  253. package/src/memory/db-init.ts +30 -3
  254. package/src/memory/embed.ts +73 -0
  255. package/src/memory/embedding-backend.ts +8 -14
  256. package/src/memory/embedding-runtime-manager.ts +12 -114
  257. package/src/memory/fingerprint.ts +2 -2
  258. package/src/memory/graph/bootstrap.ts +512 -0
  259. package/src/memory/graph/capability-seed.ts +297 -0
  260. package/src/memory/graph/consolidation.ts +691 -0
  261. package/src/memory/graph/conversation-graph-memory.ts +630 -0
  262. package/src/memory/graph/decay.test.ts +208 -0
  263. package/src/memory/graph/decay.ts +195 -0
  264. package/src/memory/graph/extraction-job.ts +69 -0
  265. package/src/memory/graph/extraction.test.ts +936 -0
  266. package/src/memory/graph/extraction.ts +1254 -0
  267. package/src/memory/graph/graph-search.ts +266 -0
  268. package/src/memory/graph/image-ref-utils.ts +29 -0
  269. package/src/memory/graph/injection.test.ts +513 -0
  270. package/src/memory/graph/injection.ts +439 -0
  271. package/src/memory/graph/inspect.ts +534 -0
  272. package/src/memory/graph/narrative.ts +267 -0
  273. package/src/memory/graph/pattern-scan.ts +269 -0
  274. package/src/memory/graph/retriever.ts +1008 -0
  275. package/src/memory/graph/scoring.test.ts +548 -0
  276. package/src/memory/graph/scoring.ts +232 -0
  277. package/src/memory/graph/serendipity.ts +65 -0
  278. package/src/memory/graph/store.test.ts +1050 -0
  279. package/src/memory/graph/store.ts +699 -0
  280. package/src/memory/graph/tool-handlers.ts +426 -0
  281. package/src/memory/graph/tools.ts +141 -0
  282. package/src/memory/graph/triggers.test.ts +487 -0
  283. package/src/memory/graph/triggers.ts +223 -0
  284. package/src/memory/graph/types.ts +271 -0
  285. package/src/memory/group-crud.ts +191 -0
  286. package/src/memory/indexer.ts +37 -19
  287. package/src/memory/job-handlers/cleanup.ts +0 -53
  288. package/src/memory/job-handlers/conversation-starters.ts +91 -53
  289. package/src/memory/job-handlers/embedding.ts +5 -31
  290. package/src/memory/job-handlers/index-maintenance.ts +23 -11
  291. package/src/memory/job-handlers/summarization.ts +32 -17
  292. package/src/memory/job-utils.ts +1 -1
  293. package/src/memory/jobs-store.ts +50 -70
  294. package/src/memory/jobs-worker.ts +147 -112
  295. package/src/memory/message-content.ts +1 -0
  296. package/src/memory/migrations/202-memory-graph-tables.ts +130 -0
  297. package/src/memory/migrations/203-drop-memory-items-tables.ts +23 -0
  298. package/src/memory/migrations/204-rename-memory-graph-type-values.ts +46 -0
  299. package/src/memory/migrations/205-memory-graph-image-refs.ts +11 -0
  300. package/src/memory/migrations/index.ts +4 -0
  301. package/src/memory/migrations/registry.ts +8 -0
  302. package/src/memory/qdrant-client.ts +44 -17
  303. package/src/memory/schema/index.ts +1 -0
  304. package/src/memory/schema/memory-graph.ts +139 -0
  305. package/src/memory/search/semantic.ts +47 -91
  306. package/src/memory/task-memory-cleanup.ts +28 -50
  307. package/src/messaging/providers/outlook/adapter.ts +8 -1
  308. package/src/messaging/providers/outlook/client.ts +299 -0
  309. package/src/messaging/providers/outlook/types.ts +118 -0
  310. package/src/notifications/adapters/macos.ts +1 -0
  311. package/src/notifications/copy-composer.ts +9 -0
  312. package/src/notifications/signal.ts +16 -0
  313. package/src/oauth/seed-providers.ts +2 -1
  314. package/src/permissions/checker.ts +24 -3
  315. package/src/permissions/defaults.ts +4 -4
  316. package/src/permissions/workspace-policy.ts +1 -1
  317. package/src/playbooks/playbook-compiler.ts +19 -18
  318. package/src/playbooks/types.ts +4 -3
  319. package/src/prompts/system-prompt.ts +3 -29
  320. package/src/providers/anthropic/client.ts +47 -19
  321. package/src/providers/gemini/client.ts +1 -1
  322. package/src/providers/openai/client.ts +1 -1
  323. package/src/providers/registry.ts +1 -1
  324. package/src/providers/retry.ts +19 -3
  325. package/src/runtime/actor-trust-resolver.ts +5 -1
  326. package/src/runtime/auth/route-policy.ts +7 -0
  327. package/src/runtime/guardian-reply-router.ts +5 -1
  328. package/src/runtime/http-server.ts +23 -3
  329. package/src/runtime/middleware/auth.ts +20 -0
  330. package/src/runtime/routes/attachment-routes.test.ts +106 -0
  331. package/src/runtime/routes/attachment-routes.ts +106 -16
  332. package/src/runtime/routes/brain-graph-routes.ts +21 -22
  333. package/src/runtime/routes/btw-routes.ts +8 -0
  334. package/src/runtime/routes/conversation-management-routes.ts +2 -0
  335. package/src/runtime/routes/conversation-starter-routes.ts +2 -2
  336. package/src/runtime/routes/debug-routes.ts +1 -1
  337. package/src/runtime/routes/global-search-routes.ts +21 -19
  338. package/src/runtime/routes/group-routes.ts +207 -0
  339. package/src/runtime/routes/guardian-action-routes.ts +21 -10
  340. package/src/runtime/routes/guardian-bootstrap-routes.ts +23 -19
  341. package/src/runtime/routes/inbound-message-handler.ts +19 -0
  342. package/src/runtime/routes/inbound-stages/guardian-activation-intercept.test.ts +292 -0
  343. package/src/runtime/routes/inbound-stages/guardian-activation-intercept.ts +207 -0
  344. package/src/runtime/routes/memory-item-routes.test.ts +2 -14
  345. package/src/runtime/routes/memory-item-routes.ts +341 -388
  346. package/src/runtime/routes/schedule-routes.ts +2 -0
  347. package/src/runtime/routes/skills-routes.ts +103 -37
  348. package/src/runtime/routes/work-items-routes.test.ts +2 -6
  349. package/src/schedule/scheduler.ts +8 -1
  350. package/src/security/oauth2.ts +1 -1
  351. package/src/security/secure-keys.ts +4 -8
  352. package/src/shared/provider-env-vars.ts +19 -0
  353. package/src/skills/catalog-cache.ts +5 -0
  354. package/src/skills/catalog-install.ts +15 -14
  355. package/src/skills/clawhub.ts +134 -154
  356. package/src/skills/install-meta.ts +208 -0
  357. package/src/skills/managed-store.ts +27 -16
  358. package/src/skills/skill-memory.ts +152 -77
  359. package/src/skills/skillssh-registry.ts +19 -17
  360. package/src/tasks/task-runner.ts +3 -1
  361. package/src/telemetry/usage-telemetry-reporter.test.ts +3 -5
  362. package/src/tools/browser/runtime-check.ts +3 -1
  363. package/src/tools/memory/register.ts +63 -46
  364. package/src/tools/permission-checker.ts +7 -1
  365. package/src/tools/shared/filesystem/image-read.ts +22 -85
  366. package/src/tools/terminal/safe-env.ts +1 -0
  367. package/src/tools/tool-manifest.ts +3 -3
  368. package/src/util/browser.ts +25 -10
  369. package/src/util/bun-runtime.ts +172 -0
  370. package/src/watcher/providers/outlook-calendar.ts +343 -0
  371. package/src/watcher/providers/outlook.ts +198 -0
  372. package/src/workspace/migrations/025-remove-oauth-app-setup-skills.ts +76 -0
  373. package/src/workspace/migrations/026-backfill-install-meta.ts +325 -0
  374. package/src/workspace/migrations/027-remove-orphaned-optimized-images-cache.ts +42 -0
  375. package/src/workspace/migrations/registry.ts +6 -0
  376. package/src/__tests__/context-memory-e2e.test.ts +0 -415
  377. package/src/__tests__/journal-context.test.ts +0 -268
  378. package/src/__tests__/memory-context-benchmark.benchmark.test.ts +0 -297
  379. package/src/__tests__/memory-lifecycle-e2e.test.ts +0 -459
  380. package/src/__tests__/memory-query-builder.test.ts +0 -59
  381. package/src/__tests__/memory-recall-quality.test.ts +0 -1046
  382. package/src/__tests__/memory-regressions.experimental.test.ts +0 -629
  383. package/src/__tests__/memory-regressions.test.ts +0 -3696
  384. package/src/__tests__/memory-retrieval.benchmark.test.ts +0 -295
  385. package/src/daemon/conversation-memory.ts +0 -207
  386. package/src/memory/conversation-starters-cadence.ts +0 -74
  387. package/src/memory/items-extractor.ts +0 -860
  388. package/src/memory/job-handlers/batch-extraction.ts +0 -753
  389. package/src/memory/job-handlers/extraction.ts +0 -40
  390. package/src/memory/job-handlers/journal-carry-forward.test.ts +0 -355
  391. package/src/memory/job-handlers/journal-carry-forward.ts +0 -255
  392. package/src/memory/journal-memory.ts +0 -224
  393. package/src/memory/query-builder.ts +0 -47
  394. package/src/memory/query-expansion.ts +0 -83
  395. package/src/memory/retriever.test.ts +0 -1592
  396. package/src/memory/retriever.ts +0 -1331
  397. package/src/memory/search/formatting.test.ts +0 -140
  398. package/src/memory/search/formatting.ts +0 -262
  399. package/src/memory/search/mmr.ts +0 -139
  400. package/src/memory/search/ranking.ts +0 -15
  401. package/src/memory/search/staleness.ts +0 -40
  402. package/src/memory/search/tier-classifier.ts +0 -18
  403. package/src/memory/search/types.ts +0 -121
  404. package/src/prompts/journal-context.ts +0 -154
  405. package/src/tools/memory/definitions.ts +0 -69
  406. package/src/tools/memory/handlers.test.ts +0 -562
  407. package/src/tools/memory/handlers.ts +0 -434
@@ -1,8 +1,6 @@
1
- import { execFileSync } from "node:child_process";
2
- import { readFileSync, statSync, unlinkSync } from "node:fs";
3
- import { tmpdir } from "node:os";
4
- import { join } from "node:path";
1
+ import { readFileSync, statSync } from "node:fs";
5
2
 
3
+ import { optimizeImageForTransport } from "../../../agent/image-optimize.js";
6
4
  import type { ImageContent } from "../../../providers/types.js";
7
5
  import type { ToolExecutionResult } from "../../types.js";
8
6
 
@@ -17,12 +15,6 @@ export const IMAGE_EXTENSIONS = new Set([
17
15
  const MAX_SIZE_BYTES = 20 * 1024 * 1024; // 20 MB — LLM API transport limit (post-optimization)
18
16
  const MAX_SOURCE_SIZE_BYTES = 100 * 1024 * 1024; // 100 MB — pre-optimization guard
19
17
 
20
- // Images above this threshold get auto-optimized via sips (macOS) to avoid
21
- // sending multi-MB base64 payloads to the LLM API.
22
- const OPTIMIZE_THRESHOLD_BYTES = 1 * 1024 * 1024; // 1 MB
23
- const OPTIMIZE_MAX_DIMENSION = 1568; // Anthropic's recommended max
24
- const OPTIMIZE_JPEG_QUALITY = 80;
25
-
26
18
  /**
27
19
  * Detect the actual image format from the first bytes of the buffer.
28
20
  * Returns the MIME type, or null if unrecognised.
@@ -69,36 +61,6 @@ function detectMediaType(buf: Buffer): string | null {
69
61
  return null;
70
62
  }
71
63
 
72
- /**
73
- * Use macOS `sips` to resize and convert an image to JPEG.
74
- * Returns the path to the optimized temp file, or null if sips is unavailable.
75
- */
76
- function optimizeWithSips(srcPath: string): string | null {
77
- const tmpPath = join(tmpdir(), `vellum-view-image-${Date.now()}.jpg`);
78
- try {
79
- execFileSync(
80
- "sips",
81
- [
82
- "--resampleHeightWidthMax",
83
- String(OPTIMIZE_MAX_DIMENSION),
84
- "-s",
85
- "format",
86
- "jpeg",
87
- "-s",
88
- "formatOptions",
89
- String(OPTIMIZE_JPEG_QUALITY),
90
- srcPath,
91
- "--out",
92
- tmpPath,
93
- ],
94
- { stdio: "pipe", timeout: 15_000 },
95
- );
96
- return tmpPath;
97
- } catch {
98
- return null;
99
- }
100
- }
101
-
102
64
  /**
103
65
  * Read an image file from disk, optionally optimize it, and return a
104
66
  * ToolExecutionResult with base64-encoded image content blocks.
@@ -130,51 +92,11 @@ export function readImageFile(resolvedPath: string): ToolExecutionResult {
130
92
  }
131
93
 
132
94
  let buffer: Buffer;
133
- let optimized = false;
134
- let tmpPath: string | null = null;
135
-
136
95
  try {
137
- if (stat.size > OPTIMIZE_THRESHOLD_BYTES) {
138
- tmpPath = optimizeWithSips(resolvedPath);
139
- if (tmpPath) {
140
- buffer = readFileSync(tmpPath) as Buffer;
141
- optimized = true;
142
- } else {
143
- // sips unavailable — fast-fail if original file exceeds the transport limit
144
- if (stat.size > MAX_SIZE_BYTES) {
145
- const sizeMB = (stat.size / (1024 * 1024)).toFixed(1);
146
- return {
147
- content: `Error: image too large (${sizeMB} MB). Maximum is 20 MB. Image optimization (sips) is unavailable on this platform.`,
148
- isError: true,
149
- };
150
- }
151
- buffer = readFileSync(resolvedPath) as Buffer;
152
- }
153
- } else {
154
- buffer = readFileSync(resolvedPath) as Buffer;
155
- }
96
+ buffer = readFileSync(resolvedPath) as Buffer;
156
97
  } catch (err) {
157
98
  const msg = err instanceof Error ? err.message : String(err);
158
99
  return { content: `Error reading file: ${msg}`, isError: true };
159
- } finally {
160
- if (tmpPath) {
161
- try {
162
- unlinkSync(tmpPath);
163
- } catch {
164
- /* ignore cleanup errors */
165
- }
166
- }
167
- }
168
-
169
- if (buffer.length > MAX_SIZE_BYTES) {
170
- const sizeMB = (buffer.length / (1024 * 1024)).toFixed(1);
171
- const msg = optimized
172
- ? `Error: image too large after optimization (${sizeMB} MB). Maximum is 20 MB.`
173
- : `Error: image too large (${sizeMB} MB). Maximum is 20 MB.`;
174
- return {
175
- content: msg,
176
- isError: true,
177
- };
178
100
  }
179
101
 
180
102
  // Detect actual format from magic bytes - never trust the file extension
@@ -187,25 +109,40 @@ export function readImageFile(resolvedPath: string): ToolExecutionResult {
187
109
  };
188
110
  }
189
111
 
190
- const base64Data = buffer.toString("base64");
112
+ // Optimize before size-checking — oversized images may compress under the limit.
113
+ const rawBase64 = buffer.toString("base64");
114
+ const { data: base64Data, mediaType: finalType } =
115
+ optimizeImageForTransport(rawBase64, detectedType);
116
+ const optimized = base64Data !== rawBase64;
117
+
118
+ const optimizedBytes = optimized
119
+ ? Math.ceil((base64Data.length * 3) / 4)
120
+ : buffer.length;
121
+ if (optimizedBytes > MAX_SIZE_BYTES) {
122
+ const sizeMB = (optimizedBytes / (1024 * 1024)).toFixed(1);
123
+ return {
124
+ content: `Error: image too large (${sizeMB} MB). Maximum is 20 MB even after optimization.`,
125
+ isError: true,
126
+ };
127
+ }
191
128
 
192
129
  const imageBlock: ImageContent = {
193
130
  type: "image" as const,
194
131
  source: {
195
132
  type: "base64" as const,
196
- media_type: detectedType,
133
+ media_type: finalType,
197
134
  data: base64Data,
198
135
  },
199
136
  };
200
137
 
201
138
  const sizeSuffix = optimized
202
139
  ? ` (optimized from ${(stat.size / 1024).toFixed(0)} KB to ${(
203
- buffer.length / 1024
140
+ optimizedBytes / 1024
204
141
  ).toFixed(0)} KB)`
205
142
  : "";
206
143
 
207
144
  return {
208
- content: `Image loaded: ${resolvedPath} (${buffer.length} bytes, ${detectedType})${sizeSuffix}`,
145
+ content: `Image loaded: ${resolvedPath} (${optimizedBytes} bytes, ${finalType})${sizeSuffix}`,
209
146
  isError: false,
210
147
  contentBlocks: [imageBlock],
211
148
  };
@@ -35,6 +35,7 @@ const SAFE_ENV_VARS = [
35
35
  "CES_CREDENTIAL_URL",
36
36
  "CES_MANAGED_MODE",
37
37
  "IS_CONTAINERIZED",
38
+ "IS_PLATFORM",
38
39
  "CES_SERVICE_TOKEN",
39
40
  ] as const;
40
41
 
@@ -18,7 +18,7 @@ import { credentialStoreTool } from "./credentials/vault.js";
18
18
  import { fileEditTool } from "./filesystem/edit.js";
19
19
  import { fileReadTool } from "./filesystem/read.js";
20
20
  import { fileWriteTool } from "./filesystem/write.js";
21
- import { memoryManageTool, memoryRecallTool } from "./memory/register.js";
21
+ import { recallTool, rememberTool } from "./memory/register.js";
22
22
  import { webFetchTool } from "./network/web-fetch.js";
23
23
  import { webSearchTool } from "./network/web-search.js";
24
24
  import { skillExecuteTool } from "./skills/execute.js";
@@ -82,8 +82,8 @@ export const explicitTools: Tool[] = [
82
82
  skillLoadTool,
83
83
  requestSystemPermissionTool,
84
84
  // Always-explicit tools
85
- memoryManageTool,
86
- memoryRecallTool,
85
+ rememberTool,
86
+ recallTool,
87
87
  credentialStoreTool,
88
88
  ];
89
89
 
@@ -1,15 +1,30 @@
1
- import { isLinux, isMacOS } from "./platform.js";
1
+ import { mkdirSync, writeFileSync } from "node:fs";
2
+ import { join } from "node:path";
3
+
4
+ import { getLogger } from "./logger.js";
5
+ import { getSignalsDir } from "./platform.js";
6
+
7
+ const log = getLogger("browser");
2
8
 
3
9
  /**
4
- * Open a URL in the user's default browser, falling back to printing the URL
5
- * to stderr on unsupported platforms.
10
+ * Open a URL on the user's host machine.
11
+ *
12
+ * Writes an `open_url` event to the `signals/emit-event` file so that the
13
+ * daemon's ConfigWatcher picks it up and publishes it to connected clients
14
+ * (e.g. the Swift macOS app) via the assistant event hub.
6
15
  */
7
- export function openInBrowser(url: string): void {
8
- if (isMacOS()) {
9
- Bun.spawn(["open", url], { stdout: "ignore", stderr: "ignore" });
10
- } else if (isLinux()) {
11
- Bun.spawn(["xdg-open", url], { stdout: "ignore", stderr: "ignore" });
12
- } else {
13
- process.stderr.write(`Open this URL to authorize:\n\n${url}\n`);
16
+ export async function openInHostBrowser(url: string): Promise<void> {
17
+ try {
18
+ const signalsDir = getSignalsDir();
19
+ mkdirSync(signalsDir, { recursive: true });
20
+ writeFileSync(
21
+ join(signalsDir, "emit-event"),
22
+ JSON.stringify({ type: "open_url", url }),
23
+ );
24
+ } catch (err) {
25
+ log.warn(
26
+ { error: err instanceof Error ? err.message : String(err) },
27
+ "Failed to write open_url signal",
28
+ );
14
29
  }
15
30
  }
@@ -0,0 +1,172 @@
1
+ /**
2
+ * Shared helper for locating or JIT-installing a standalone `bun` binary.
3
+ *
4
+ * Several subsystems (package resolver, hook runner, browser runtime,
5
+ * credential execution, embedding runtime) need to spawn `bun` as a child
6
+ * process. Inside a `bun build --compile` binary, `process.execPath` is the
7
+ * compiled app — not the bun CLI — and the user may not have bun on PATH.
8
+ *
9
+ * This module checks well-known locations first, and if none is found it
10
+ * downloads a pinned release from GitHub into $VELLUM_WORKSPACE_DIR/bin/.
11
+ */
12
+
13
+ import {
14
+ chmodSync,
15
+ existsSync,
16
+ mkdirSync,
17
+ renameSync,
18
+ rmSync,
19
+ writeFileSync,
20
+ } from "node:fs";
21
+ import { arch, homedir, platform } from "node:os";
22
+ import { basename, join } from "node:path";
23
+
24
+ import { getLogger } from "./logger.js";
25
+ import { getBinDir } from "./platform.js";
26
+
27
+ const log = getLogger("bun-runtime");
28
+
29
+ /** Pinned bun version to download when no system bun is available. */
30
+ const BUN_VERSION = "1.2.0";
31
+
32
+ /** Module-level cache so we only resolve/download once per process. */
33
+ let cachedBunPath: string | undefined;
34
+
35
+ /** In-flight download promise to deduplicate concurrent callers. */
36
+ let inflightDownload: Promise<string> | undefined;
37
+
38
+ /**
39
+ * Return a path to a usable `bun` binary, downloading one if necessary.
40
+ *
41
+ * Resolution order:
42
+ * 1. `process.execPath` if it IS the bun CLI (dev mode)
43
+ * 2. Previously downloaded copy at $VELLUM_WORKSPACE_DIR/bin/bun
44
+ * 3. Common install locations (~/.bun/bin/bun, /opt/homebrew/bin/bun, etc.)
45
+ * 4. `Bun.which("bun")` (PATH lookup)
46
+ * 5. Download from GitHub releases into $VELLUM_WORKSPACE_DIR/bin/
47
+ */
48
+ export async function ensureBun(): Promise<string> {
49
+ if (cachedBunPath && existsSync(cachedBunPath)) {
50
+ return cachedBunPath;
51
+ }
52
+
53
+ const found = findBun();
54
+ if (found) {
55
+ cachedBunPath = found;
56
+ return found;
57
+ }
58
+
59
+ // No bun found anywhere — download it.
60
+ // Use an in-flight promise to deduplicate concurrent callers.
61
+ if (!inflightDownload) {
62
+ log.info("No bun binary found, downloading…");
63
+ const binDir = getBinDir();
64
+ inflightDownload = downloadBun(binDir).finally(() => {
65
+ inflightDownload = undefined;
66
+ });
67
+ }
68
+ const downloaded = await inflightDownload;
69
+ cachedBunPath = downloaded;
70
+ return downloaded;
71
+ }
72
+
73
+ /**
74
+ * Synchronous check for an already-available bun binary.
75
+ * Returns the path if found, undefined otherwise. Does NOT download.
76
+ */
77
+ export function findBun(): string | undefined {
78
+ // 1. process.execPath if it is the bun CLI itself (dev mode)
79
+ const execBase = basename(process.execPath);
80
+ if (execBase === "bun" || execBase === "bun.exe") {
81
+ return process.execPath;
82
+ }
83
+
84
+ // 2. Previously downloaded copy
85
+ const downloaded = join(getBinDir(), "bun");
86
+ if (existsSync(downloaded)) return downloaded;
87
+
88
+ // 3. Common install locations
89
+ const home = homedir();
90
+ for (const p of [
91
+ join(home, ".bun", "bin", "bun"),
92
+ "/opt/homebrew/bin/bun",
93
+ "/usr/local/bin/bun",
94
+ ]) {
95
+ if (existsSync(p)) return p;
96
+ }
97
+
98
+ // 4. PATH lookup
99
+ const which = Bun.which("bun");
100
+ if (which) return which;
101
+
102
+ return undefined;
103
+ }
104
+
105
+ /**
106
+ * Download a pinned bun release into the given directory.
107
+ * Returns the absolute path to the downloaded binary.
108
+ */
109
+ async function downloadBun(installDir: string): Promise<string> {
110
+ const os = platform();
111
+ const cpu = arch() === "arm64" ? "aarch64" : arch();
112
+ const target = `${os}-${cpu}`;
113
+ const url = `https://github.com/oven-sh/bun/releases/download/bun-v${BUN_VERSION}/bun-${target}.zip`;
114
+
115
+ log.info({ url, target, bunVersion: BUN_VERSION }, "Downloading bun binary");
116
+
117
+ const response = await fetch(url, { redirect: "follow" });
118
+ if (!response.ok) {
119
+ throw new Error(
120
+ `Failed to download bun: ${response.status} ${response.statusText}`,
121
+ );
122
+ }
123
+
124
+ const zipData = await response.arrayBuffer();
125
+ mkdirSync(installDir, { recursive: true });
126
+
127
+ const tmpZip = join(installDir, `bun-download-${Date.now()}.zip`);
128
+ writeFileSync(tmpZip, Buffer.from(zipData));
129
+
130
+ try {
131
+ const proc = Bun.spawn({
132
+ cmd: ["unzip", "-o", tmpZip, "-d", installDir],
133
+ stdout: "ignore",
134
+ stderr: "pipe",
135
+ });
136
+ await proc.exited;
137
+ if (proc.exitCode !== 0) {
138
+ const stderr = await new Response(proc.stderr).text();
139
+ throw new Error(`Failed to extract bun zip: ${stderr}`);
140
+ }
141
+
142
+ // Move binary from bun-{target}/bun to installDir/bun
143
+ const extractedBun = join(installDir, `bun-${target}`, "bun");
144
+ const finalPath = join(installDir, "bun");
145
+ if (existsSync(extractedBun)) {
146
+ // Remove old binary first to avoid "Text file busy" on some systems
147
+ if (existsSync(finalPath)) {
148
+ rmSync(finalPath);
149
+ }
150
+ renameSync(extractedBun, finalPath);
151
+ rmSync(join(installDir, `bun-${target}`), {
152
+ recursive: true,
153
+ force: true,
154
+ });
155
+ } else if (!existsSync(finalPath)) {
156
+ throw new Error(
157
+ `Bun binary not found at expected path after extraction: ${extractedBun}`,
158
+ );
159
+ }
160
+
161
+ chmodSync(finalPath, 0o755);
162
+
163
+ log.info({ path: finalPath }, "Bun binary downloaded successfully");
164
+ return finalPath;
165
+ } finally {
166
+ try {
167
+ rmSync(tmpZip);
168
+ } catch {
169
+ /* ignore cleanup failure */
170
+ }
171
+ }
172
+ }