@vellumai/assistant 0.4.17 → 0.4.19

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 (528) hide show
  1. package/docs/runbook-trusted-contacts.md +5 -3
  2. package/eslint.config.mjs +2 -2
  3. package/package.json +1 -1
  4. package/src/__tests__/access-request-decision.test.ts +128 -120
  5. package/src/__tests__/account-registry.test.ts +121 -110
  6. package/src/__tests__/active-skill-tools.test.ts +200 -172
  7. package/src/__tests__/actor-token-service.test.ts +341 -274
  8. package/src/__tests__/agent-loop-thinking.test.ts +28 -19
  9. package/src/__tests__/agent-loop.test.ts +798 -378
  10. package/src/__tests__/anthropic-provider.test.ts +405 -247
  11. package/src/__tests__/app-builder-tool-scripts.test.ts +97 -97
  12. package/src/__tests__/app-bundler.test.ts +112 -79
  13. package/src/__tests__/app-executors.test.ts +205 -178
  14. package/src/__tests__/app-git-history.test.ts +90 -73
  15. package/src/__tests__/app-git-service.test.ts +67 -53
  16. package/src/__tests__/app-open-proxy.test.ts +29 -25
  17. package/src/__tests__/approval-conversation-turn.test.ts +100 -81
  18. package/src/__tests__/approval-hardcoded-copy-guard.test.ts +45 -17
  19. package/src/__tests__/approval-message-composer.test.ts +119 -119
  20. package/src/__tests__/approval-primitive.test.ts +264 -233
  21. package/src/__tests__/approval-routes-http.test.ts +4 -3
  22. package/src/__tests__/asset-materialize-tool.test.ts +250 -178
  23. package/src/__tests__/asset-search-tool.test.ts +251 -191
  24. package/src/__tests__/assistant-attachment-directive.test.ts +187 -142
  25. package/src/__tests__/assistant-attachments.test.ts +254 -186
  26. package/src/__tests__/assistant-event-hub.test.ts +105 -63
  27. package/src/__tests__/assistant-event.test.ts +66 -58
  28. package/src/__tests__/assistant-events-sse-hardening.test.ts +113 -73
  29. package/src/__tests__/assistant-feature-flag-guard.test.ts +78 -52
  30. package/src/__tests__/assistant-feature-flag-guardrails.test.ts +48 -45
  31. package/src/__tests__/assistant-feature-flags-integration.test.ts +118 -77
  32. package/src/__tests__/assistant-id-boundary-guard.test.ts +158 -104
  33. package/src/__tests__/attachments-store.test.ts +240 -183
  34. package/src/__tests__/attachments.test.ts +70 -62
  35. package/src/__tests__/audit-log-rotation.test.ts +50 -35
  36. package/src/__tests__/browser-fill-credential.test.ts +169 -101
  37. package/src/__tests__/browser-manager.test.ts +97 -75
  38. package/src/__tests__/browser-runtime-check.test.ts +16 -15
  39. package/src/__tests__/browser-skill-baseline-tool-payload.test.ts +12 -10
  40. package/src/__tests__/browser-skill-endstate.test.ts +97 -72
  41. package/src/__tests__/bundle-scanner.test.ts +47 -22
  42. package/src/__tests__/bundled-asset.test.ts +74 -47
  43. package/src/__tests__/call-constants.test.ts +19 -19
  44. package/src/__tests__/call-controller.test.ts +0 -1
  45. package/src/__tests__/call-conversation-messages.test.ts +90 -65
  46. package/src/__tests__/call-domain.test.ts +149 -121
  47. package/src/__tests__/call-pointer-message-composer.test.ts +113 -83
  48. package/src/__tests__/call-pointer-messages.test.ts +213 -154
  49. package/src/__tests__/call-pointer-no-hardcoded-copy.guard.test.ts +9 -10
  50. package/src/__tests__/call-recovery.test.ts +232 -212
  51. package/src/__tests__/call-routes-http.test.ts +0 -1
  52. package/src/__tests__/call-start-guardian-guard.test.ts +32 -30
  53. package/src/__tests__/call-state-machine.test.ts +62 -51
  54. package/src/__tests__/call-state.test.ts +89 -75
  55. package/src/__tests__/call-store.test.ts +387 -316
  56. package/src/__tests__/callback-handoff-copy.test.ts +84 -82
  57. package/src/__tests__/canonical-guardian-store.test.ts +331 -280
  58. package/src/__tests__/channel-approval-routes.test.ts +1643 -1115
  59. package/src/__tests__/channel-approval.test.ts +139 -137
  60. package/src/__tests__/channel-approvals.test.ts +7 -2
  61. package/src/__tests__/channel-delivery-store.test.ts +232 -194
  62. package/src/__tests__/channel-guardian.test.ts +5 -3
  63. package/src/__tests__/channel-invite-transport.test.ts +107 -92
  64. package/src/__tests__/channel-policy.test.ts +42 -38
  65. package/src/__tests__/channel-readiness-service.test.ts +119 -102
  66. package/src/__tests__/channel-reply-delivery.test.ts +147 -118
  67. package/src/__tests__/channel-retry-sweep.test.ts +153 -110
  68. package/src/__tests__/checker.test.ts +3309 -1850
  69. package/src/__tests__/clarification-resolver.test.ts +91 -79
  70. package/src/__tests__/classifier.test.ts +64 -54
  71. package/src/__tests__/claude-code-skill-regression.test.ts +42 -37
  72. package/src/__tests__/claude-code-tool-profiles.test.ts +31 -29
  73. package/src/__tests__/clawhub.test.ts +92 -82
  74. package/src/__tests__/cli.test.ts +30 -30
  75. package/src/__tests__/clipboard.test.ts +53 -46
  76. package/src/__tests__/commit-guarantee.test.ts +59 -52
  77. package/src/__tests__/commit-message-enrichment-service.test.ts +203 -75
  78. package/src/__tests__/compaction.benchmark.test.ts +33 -31
  79. package/src/__tests__/computer-use-session-compaction.test.ts +60 -50
  80. package/src/__tests__/computer-use-session-lifecycle.test.ts +145 -117
  81. package/src/__tests__/computer-use-session-working-dir.test.ts +62 -48
  82. package/src/__tests__/computer-use-skill-baseline.test.ts +22 -19
  83. package/src/__tests__/computer-use-skill-endstate.test.ts +45 -31
  84. package/src/__tests__/computer-use-skill-lifecycle-cleanup.test.ts +121 -88
  85. package/src/__tests__/computer-use-skill-manifest-regression.test.ts +65 -42
  86. package/src/__tests__/computer-use-skill-proxy-bridge.test.ts +33 -18
  87. package/src/__tests__/computer-use-tools.test.ts +121 -98
  88. package/src/__tests__/config-schema.test.ts +443 -347
  89. package/src/__tests__/config-watcher.test.ts +96 -81
  90. package/src/__tests__/confirmation-request-guardian-bridge.test.ts +148 -133
  91. package/src/__tests__/conflict-intent-tokenization.test.ts +96 -78
  92. package/src/__tests__/conflict-policy.test.ts +151 -80
  93. package/src/__tests__/conflict-store.test.ts +203 -157
  94. package/src/__tests__/connection-policy.test.ts +89 -59
  95. package/src/__tests__/contacts-tools.test.ts +247 -178
  96. package/src/__tests__/context-memory-e2e.test.ts +306 -214
  97. package/src/__tests__/context-token-estimator.test.ts +114 -74
  98. package/src/__tests__/context-window-manager.test.ts +269 -167
  99. package/src/__tests__/contradiction-checker.test.ts +161 -135
  100. package/src/__tests__/conversation-attention-store.test.ts +350 -290
  101. package/src/__tests__/conversation-attention-telegram.test.ts +0 -1
  102. package/src/__tests__/conversation-pairing.test.ts +220 -113
  103. package/src/__tests__/conversation-routes-guardian-reply.test.ts +8 -0
  104. package/src/__tests__/conversation-store.test.ts +390 -235
  105. package/src/__tests__/credential-broker-browser-fill.test.ts +325 -250
  106. package/src/__tests__/credential-broker-server-use.test.ts +283 -243
  107. package/src/__tests__/credential-broker.test.ts +128 -74
  108. package/src/__tests__/credential-host-pattern-match.test.ts +64 -44
  109. package/src/__tests__/credential-metadata-store.test.ts +360 -311
  110. package/src/__tests__/credential-policy-validate.test.ts +81 -65
  111. package/src/__tests__/credential-resolve.test.ts +212 -145
  112. package/src/__tests__/credential-security-e2e.test.ts +144 -103
  113. package/src/__tests__/credential-security-invariants.test.ts +253 -208
  114. package/src/__tests__/credential-selection.test.ts +254 -146
  115. package/src/__tests__/credential-vault-unit.test.ts +531 -341
  116. package/src/__tests__/credential-vault.test.ts +761 -484
  117. package/src/__tests__/daemon-assistant-events.test.ts +91 -66
  118. package/src/__tests__/daemon-lifecycle.test.ts +258 -190
  119. package/src/__tests__/daemon-server-session-init.test.ts +2 -1
  120. package/src/__tests__/date-context.test.ts +314 -249
  121. package/src/__tests__/db-migration-rollback.test.ts +259 -130
  122. package/src/__tests__/db-schedule-syntax-migration.test.ts +78 -41
  123. package/src/__tests__/delete-managed-skill-tool.test.ts +77 -53
  124. package/src/__tests__/deterministic-verification-control-plane.test.ts +0 -1
  125. package/src/__tests__/dictation-mode-detection.test.ts +77 -55
  126. package/src/__tests__/dictation-profile-store.test.ts +70 -56
  127. package/src/__tests__/dictation-text-processing.test.ts +53 -35
  128. package/src/__tests__/diff.test.ts +102 -98
  129. package/src/__tests__/domain-normalize.test.ts +54 -54
  130. package/src/__tests__/domain-policy.test.ts +71 -55
  131. package/src/__tests__/dynamic-page-surface.test.ts +31 -33
  132. package/src/__tests__/dynamic-skill-workflow-prompt.test.ts +69 -69
  133. package/src/__tests__/edit-engine.test.ts +56 -56
  134. package/src/__tests__/elevenlabs-client.test.ts +117 -91
  135. package/src/__tests__/elevenlabs-config.test.ts +32 -31
  136. package/src/__tests__/email-classifier.test.ts +15 -12
  137. package/src/__tests__/email-cli.test.ts +121 -108
  138. package/src/__tests__/emit-signal-routing-intent.test.ts +76 -69
  139. package/src/__tests__/encrypted-store.test.ts +180 -154
  140. package/src/__tests__/entity-extractor.test.ts +108 -87
  141. package/src/__tests__/entity-search.test.ts +664 -258
  142. package/src/__tests__/ephemeral-permissions.test.ts +224 -188
  143. package/src/__tests__/event-bus.test.ts +81 -77
  144. package/src/__tests__/extract-email.test.ts +29 -20
  145. package/src/__tests__/file-edit-tool.test.ts +62 -44
  146. package/src/__tests__/file-ops-service.test.ts +131 -114
  147. package/src/__tests__/file-read-tool.test.ts +48 -31
  148. package/src/__tests__/file-write-tool.test.ts +43 -37
  149. package/src/__tests__/filesystem-tools.test.ts +238 -209
  150. package/src/__tests__/followup-tools.test.ts +237 -162
  151. package/src/__tests__/forbidden-legacy-symbols.test.ts +19 -20
  152. package/src/__tests__/frontmatter.test.ts +96 -81
  153. package/src/__tests__/fuzzy-match-property.test.ts +75 -81
  154. package/src/__tests__/fuzzy-match.test.ts +71 -65
  155. package/src/__tests__/gateway-client-managed-outbound.test.ts +76 -57
  156. package/src/__tests__/gateway-only-enforcement.test.ts +0 -1
  157. package/src/__tests__/gateway-only-guard.test.ts +0 -1
  158. package/src/__tests__/gemini-image-service.test.ts +113 -100
  159. package/src/__tests__/gemini-provider.test.ts +297 -220
  160. package/src/__tests__/get-weather.test.ts +188 -114
  161. package/src/__tests__/gmail-integration.test.ts +13 -5
  162. package/src/__tests__/guardian-action-conversation-turn.test.ts +226 -171
  163. package/src/__tests__/guardian-action-copy-generator.test.ts +111 -93
  164. package/src/__tests__/guardian-action-followup-executor.test.ts +0 -1
  165. package/src/__tests__/guardian-action-followup-store.test.ts +199 -167
  166. package/src/__tests__/guardian-action-grant-mint-consume.test.ts +297 -250
  167. package/src/__tests__/guardian-action-late-reply.test.ts +462 -316
  168. package/src/__tests__/guardian-action-no-hardcoded-copy.test.ts +23 -18
  169. package/src/__tests__/guardian-action-store.test.ts +158 -109
  170. package/src/__tests__/guardian-action-sweep.test.ts +114 -100
  171. package/src/__tests__/guardian-actions-endpoint.test.ts +440 -256
  172. package/src/__tests__/guardian-control-plane-policy.test.ts +497 -331
  173. package/src/__tests__/guardian-decision-primitive-canonical.test.ts +217 -215
  174. package/src/__tests__/guardian-dispatch.test.ts +316 -256
  175. package/src/__tests__/guardian-grant-minting.test.ts +247 -178
  176. package/src/__tests__/guardian-outbound-http.test.ts +5 -3
  177. package/src/__tests__/guardian-principal-id-roundtrip.test.ts +99 -96
  178. package/src/__tests__/guardian-question-copy.test.ts +17 -17
  179. package/src/__tests__/guardian-question-mode.test.ts +134 -100
  180. package/src/__tests__/guardian-routing-invariants.test.ts +0 -1
  181. package/src/__tests__/guardian-routing-state.test.ts +0 -1
  182. package/src/__tests__/guardian-verification-intent-routing.test.ts +94 -88
  183. package/src/__tests__/guardian-verification-voice-binding.test.ts +0 -1
  184. package/src/__tests__/guardian-verify-setup-skill-regression.test.ts +0 -1
  185. package/src/__tests__/handle-user-message-secret-resume.test.ts +7 -2
  186. package/src/__tests__/handlers-add-trust-rule-metadata.test.ts +92 -76
  187. package/src/__tests__/handlers-cu-observation-blob.test.ts +103 -70
  188. package/src/__tests__/handlers-ipc-blob-probe.test.ts +77 -51
  189. package/src/__tests__/handlers-slack-config.test.ts +63 -54
  190. package/src/__tests__/handlers-task-submit-slash.test.ts +18 -18
  191. package/src/__tests__/handlers-telegram-config.test.ts +662 -329
  192. package/src/__tests__/handlers-twitter-config.test.ts +525 -298
  193. package/src/__tests__/handlers-user-message-approval-consumption.test.ts +5 -2
  194. package/src/__tests__/headless-browser-interactions.test.ts +444 -280
  195. package/src/__tests__/headless-browser-navigate.test.ts +116 -79
  196. package/src/__tests__/headless-browser-read-tools.test.ts +123 -86
  197. package/src/__tests__/headless-browser-snapshot.test.ts +71 -56
  198. package/src/__tests__/heartbeat-service.test.ts +76 -58
  199. package/src/__tests__/history-repair-observability.test.ts +14 -14
  200. package/src/__tests__/history-repair.test.ts +171 -167
  201. package/src/__tests__/home-base-bootstrap.test.ts +30 -27
  202. package/src/__tests__/hooks-blocking.test.ts +86 -37
  203. package/src/__tests__/hooks-cli.test.ts +104 -68
  204. package/src/__tests__/hooks-config.test.ts +81 -43
  205. package/src/__tests__/hooks-discovery.test.ts +106 -96
  206. package/src/__tests__/hooks-integration.test.ts +78 -72
  207. package/src/__tests__/hooks-manager.test.ts +99 -61
  208. package/src/__tests__/hooks-runner.test.ts +94 -71
  209. package/src/__tests__/hooks-settings.test.ts +69 -64
  210. package/src/__tests__/hooks-templates.test.ts +85 -54
  211. package/src/__tests__/hooks-ts-runner.test.ts +82 -45
  212. package/src/__tests__/hooks-watch.test.ts +32 -22
  213. package/src/__tests__/host-file-edit-tool.test.ts +190 -148
  214. package/src/__tests__/host-file-read-tool.test.ts +86 -63
  215. package/src/__tests__/host-file-write-tool.test.ts +98 -64
  216. package/src/__tests__/host-shell-tool.test.ts +342 -233
  217. package/src/__tests__/inbound-invite-redemption.test.ts +0 -1
  218. package/src/__tests__/ingress-member-store.test.ts +163 -159
  219. package/src/__tests__/ingress-reconcile.test.ts +13 -6
  220. package/src/__tests__/ingress-routes-http.test.ts +441 -356
  221. package/src/__tests__/ingress-url-consistency.test.ts +125 -64
  222. package/src/__tests__/integration-status.test.ts +93 -73
  223. package/src/__tests__/intent-routing.test.ts +148 -118
  224. package/src/__tests__/invite-redemption-service.test.ts +163 -121
  225. package/src/__tests__/ipc-blob-store.test.ts +104 -91
  226. package/src/__tests__/ipc-contract-inventory.test.ts +27 -15
  227. package/src/__tests__/ipc-contract.test.ts +24 -23
  228. package/src/__tests__/ipc-protocol.test.ts +52 -46
  229. package/src/__tests__/ipc-roundtrip.benchmark.test.ts +61 -50
  230. package/src/__tests__/ipc-snapshot.test.ts +1135 -1056
  231. package/src/__tests__/ipc-validate.test.ts +240 -179
  232. package/src/__tests__/key-migration.test.ts +123 -90
  233. package/src/__tests__/keychain.test.ts +150 -123
  234. package/src/__tests__/lifecycle-docs-guard.test.ts +65 -64
  235. package/src/__tests__/llm-usage-store.test.ts +112 -87
  236. package/src/__tests__/managed-skill-lifecycle.test.ts +147 -108
  237. package/src/__tests__/managed-store.test.ts +411 -360
  238. package/src/__tests__/mcp-cli.test.ts +190 -124
  239. package/src/__tests__/mcp-health-check.test.ts +26 -21
  240. package/src/__tests__/media-generate-image.test.ts +122 -99
  241. package/src/__tests__/media-reuse-story.e2e.test.ts +282 -214
  242. package/src/__tests__/media-visibility-policy.test.ts +86 -38
  243. package/src/__tests__/memory-context-benchmark.benchmark.test.ts +146 -100
  244. package/src/__tests__/memory-lifecycle-e2e.test.ts +385 -297
  245. package/src/__tests__/memory-query-builder.test.ts +32 -33
  246. package/src/__tests__/memory-recall-quality.test.ts +761 -407
  247. package/src/__tests__/memory-regressions.experimental.test.ts +443 -380
  248. package/src/__tests__/memory-regressions.test.ts +3725 -2642
  249. package/src/__tests__/memory-retrieval-budget.test.ts +7 -8
  250. package/src/__tests__/memory-retrieval.benchmark.test.ts +144 -109
  251. package/src/__tests__/memory-upsert-concurrency.test.ts +292 -201
  252. package/src/__tests__/messaging-send-tool.test.ts +36 -29
  253. package/src/__tests__/migration-cli-flows.test.ts +69 -53
  254. package/src/__tests__/migration-ordering.test.ts +103 -86
  255. package/src/__tests__/mime-builder.test.ts +55 -32
  256. package/src/__tests__/mock-signup-server.test.ts +384 -246
  257. package/src/__tests__/model-intents.test.ts +61 -37
  258. package/src/__tests__/no-direct-anthropic-sdk-imports.test.ts +9 -12
  259. package/src/__tests__/no-is-trusted-guard.test.ts +24 -21
  260. package/src/__tests__/non-member-access-request.test.ts +3 -2
  261. package/src/__tests__/notification-broadcaster.test.ts +99 -81
  262. package/src/__tests__/notification-decision-fallback.test.ts +223 -178
  263. package/src/__tests__/notification-decision-strategy.test.ts +375 -337
  264. package/src/__tests__/notification-deep-link.test.ts +67 -61
  265. package/src/__tests__/notification-guardian-path.test.ts +248 -206
  266. package/src/__tests__/notification-routing-intent.test.ts +166 -93
  267. package/src/__tests__/notification-thread-candidate-validation.test.ts +78 -75
  268. package/src/__tests__/notification-thread-candidates.test.ts +64 -61
  269. package/src/__tests__/oauth-callback-registry.test.ts +40 -30
  270. package/src/__tests__/oauth-connect-handler.test.ts +109 -89
  271. package/src/__tests__/oauth-scope-policy.test.ts +63 -55
  272. package/src/__tests__/oauth2-gateway-transport.test.ts +252 -174
  273. package/src/__tests__/onboarding-starter-tasks.test.ts +93 -89
  274. package/src/__tests__/onboarding-template-contract.test.ts +93 -94
  275. package/src/__tests__/openai-provider.test.ts +366 -274
  276. package/src/__tests__/pairing-concurrent.test.ts +18 -12
  277. package/src/__tests__/pairing-routes.test.ts +45 -41
  278. package/src/__tests__/parallel-tool.benchmark.test.ts +108 -58
  279. package/src/__tests__/parser.test.ts +316 -226
  280. package/src/__tests__/path-classifier.test.ts +24 -25
  281. package/src/__tests__/path-policy.test.ts +187 -147
  282. package/src/__tests__/phone.test.ts +36 -36
  283. package/src/__tests__/platform-move-helper.test.ts +48 -40
  284. package/src/__tests__/platform-socket-path.test.ts +23 -24
  285. package/src/__tests__/platform-workspace-migration.test.ts +464 -414
  286. package/src/__tests__/platform.test.ts +61 -53
  287. package/src/__tests__/playbook-execution.test.ts +397 -265
  288. package/src/__tests__/playbook-tools.test.ts +267 -196
  289. package/src/__tests__/prebuilt-home-base-seed.test.ts +30 -27
  290. package/src/__tests__/pricing.test.ts +316 -136
  291. package/src/__tests__/profile-compiler.test.ts +206 -188
  292. package/src/__tests__/provider-commit-message-generator.test.ts +114 -106
  293. package/src/__tests__/provider-error-scenarios.test.ts +212 -158
  294. package/src/__tests__/provider-fail-open-selection.test.ts +51 -44
  295. package/src/__tests__/provider-registry-ollama.test.ts +13 -9
  296. package/src/__tests__/provider-streaming.benchmark.test.ts +232 -183
  297. package/src/__tests__/proxy-approval-callback.test.ts +180 -119
  298. package/src/__tests__/public-ingress-urls.test.ts +112 -94
  299. package/src/__tests__/qdrant-manager.test.ts +147 -98
  300. package/src/__tests__/ratelimit.test.ts +152 -82
  301. package/src/__tests__/recording-handler.test.ts +273 -151
  302. package/src/__tests__/recording-intent-fallback.test.ts +94 -75
  303. package/src/__tests__/recording-intent-handler.test.ts +9 -2
  304. package/src/__tests__/recording-intent.test.ts +578 -379
  305. package/src/__tests__/recording-state-machine.test.ts +530 -316
  306. package/src/__tests__/recurrence-engine-rruleset.test.ts +150 -92
  307. package/src/__tests__/recurrence-engine.test.ts +81 -41
  308. package/src/__tests__/recurrence-types.test.ts +63 -44
  309. package/src/__tests__/relay-server.test.ts +2131 -1602
  310. package/src/__tests__/reminder-store.test.ts +158 -80
  311. package/src/__tests__/reminder.test.ts +113 -109
  312. package/src/__tests__/remote-skill-policy.test.ts +96 -72
  313. package/src/__tests__/request-file-tool.test.ts +74 -67
  314. package/src/__tests__/response-tier.test.ts +131 -74
  315. package/src/__tests__/runtime-attachment-metadata.test.ts +0 -1
  316. package/src/__tests__/runtime-events-sse-parity.test.ts +167 -145
  317. package/src/__tests__/runtime-events-sse.test.ts +0 -1
  318. package/src/__tests__/sandbox-diagnostics.test.ts +66 -56
  319. package/src/__tests__/sandbox-host-parity.test.ts +377 -301
  320. package/src/__tests__/scaffold-managed-skill-tool.test.ts +213 -161
  321. package/src/__tests__/schedule-store.test.ts +268 -205
  322. package/src/__tests__/schedule-tools.test.ts +702 -524
  323. package/src/__tests__/scheduler-recurrence.test.ts +240 -130
  324. package/src/__tests__/scoped-approval-grants.test.ts +258 -168
  325. package/src/__tests__/scoped-grant-security-matrix.test.ts +160 -146
  326. package/src/__tests__/script-proxy-certs.test.ts +38 -35
  327. package/src/__tests__/script-proxy-connect-tunnel.test.ts +71 -46
  328. package/src/__tests__/script-proxy-decision-trace.test.ts +161 -84
  329. package/src/__tests__/script-proxy-http-forwarder.test.ts +146 -129
  330. package/src/__tests__/script-proxy-injection-runtime.test.ts +139 -113
  331. package/src/__tests__/script-proxy-mitm-handler.test.ts +226 -142
  332. package/src/__tests__/script-proxy-policy-runtime.test.ts +126 -86
  333. package/src/__tests__/script-proxy-policy.test.ts +308 -153
  334. package/src/__tests__/script-proxy-rewrite-specificity.test.ts +74 -62
  335. package/src/__tests__/script-proxy-router.test.ts +111 -77
  336. package/src/__tests__/script-proxy-session-manager.test.ts +156 -113
  337. package/src/__tests__/script-proxy-session-runtime.test.ts +28 -24
  338. package/src/__tests__/secret-allowlist.test.ts +105 -90
  339. package/src/__tests__/secret-ingress-handler.test.ts +41 -30
  340. package/src/__tests__/secret-onetime-send.test.ts +67 -50
  341. package/src/__tests__/secret-prompt-log-hygiene.test.ts +35 -31
  342. package/src/__tests__/secret-response-routing.test.ts +50 -41
  343. package/src/__tests__/secret-scanner-executor.test.ts +152 -111
  344. package/src/__tests__/secret-scanner.test.ts +495 -413
  345. package/src/__tests__/secure-keys.test.ts +132 -121
  346. package/src/__tests__/send-endpoint-busy.test.ts +8 -3
  347. package/src/__tests__/send-notification-tool.test.ts +43 -42
  348. package/src/__tests__/sensitive-output-placeholders.test.ts +72 -64
  349. package/src/__tests__/sequence-store.test.ts +335 -167
  350. package/src/__tests__/server-history-render.test.ts +341 -202
  351. package/src/__tests__/session-abort-tool-results.test.ts +133 -70
  352. package/src/__tests__/session-confirmation-signals.test.ts +252 -160
  353. package/src/__tests__/session-conflict-gate.test.ts +775 -585
  354. package/src/__tests__/session-error.test.ts +222 -191
  355. package/src/__tests__/session-evictor.test.ts +79 -62
  356. package/src/__tests__/session-init.benchmark.test.ts +170 -108
  357. package/src/__tests__/session-load-history-repair.test.ts +273 -139
  358. package/src/__tests__/session-messaging-secret-redirect.test.ts +130 -90
  359. package/src/__tests__/session-pre-run-repair.test.ts +106 -59
  360. package/src/__tests__/session-profile-injection.test.ts +198 -130
  361. package/src/__tests__/session-provider-retry-repair.test.ts +223 -141
  362. package/src/__tests__/session-queue.test.ts +624 -321
  363. package/src/__tests__/session-runtime-assembly.test.ts +425 -329
  364. package/src/__tests__/session-runtime-workspace.test.ts +69 -61
  365. package/src/__tests__/session-skill-tools.test.ts +973 -678
  366. package/src/__tests__/session-slash-known.test.ts +185 -133
  367. package/src/__tests__/session-slash-queue.test.ts +147 -81
  368. package/src/__tests__/session-slash-unknown.test.ts +135 -90
  369. package/src/__tests__/session-surfaces-task-progress.test.ts +122 -87
  370. package/src/__tests__/session-tool-setup-app-refresh.test.ts +338 -177
  371. package/src/__tests__/session-tool-setup-memory-scope.test.ts +63 -40
  372. package/src/__tests__/session-tool-setup-side-effect-flag.test.ts +60 -37
  373. package/src/__tests__/session-tool-setup-tools-disabled.test.ts +28 -26
  374. package/src/__tests__/session-undo.test.ts +43 -30
  375. package/src/__tests__/session-workspace-cache-state.test.ts +108 -67
  376. package/src/__tests__/session-workspace-injection.test.ts +245 -117
  377. package/src/__tests__/session-workspace-tool-tracking.test.ts +260 -93
  378. package/src/__tests__/shared-filesystem-errors.test.ts +47 -47
  379. package/src/__tests__/shell-credential-ref.test.ts +126 -90
  380. package/src/__tests__/shell-identity.test.ts +134 -111
  381. package/src/__tests__/shell-parser-fuzz.test.ts +263 -179
  382. package/src/__tests__/shell-parser-property.test.ts +435 -288
  383. package/src/__tests__/shell-tool-proxy-mode.test.ts +142 -70
  384. package/src/__tests__/size-guard.test.ts +42 -44
  385. package/src/__tests__/skill-feature-flags-integration.test.ts +79 -52
  386. package/src/__tests__/skill-feature-flags.test.ts +75 -47
  387. package/src/__tests__/skill-include-graph.test.ts +143 -148
  388. package/src/__tests__/skill-load-feature-flag.test.ts +94 -59
  389. package/src/__tests__/skill-load-tool.test.ts +371 -199
  390. package/src/__tests__/skill-projection-feature-flag.test.ts +131 -88
  391. package/src/__tests__/skill-projection.benchmark.test.ts +93 -65
  392. package/src/__tests__/skill-script-runner-host.test.ts +460 -250
  393. package/src/__tests__/skill-script-runner-sandbox.test.ts +168 -108
  394. package/src/__tests__/skill-script-runner.test.ts +115 -74
  395. package/src/__tests__/skill-tool-factory.test.ts +140 -96
  396. package/src/__tests__/skill-tool-manifest.test.ts +306 -210
  397. package/src/__tests__/skill-version-hash.test.ts +70 -56
  398. package/src/__tests__/skills.test.ts +0 -1
  399. package/src/__tests__/slack-channel-config.test.ts +127 -84
  400. package/src/__tests__/slack-skill.test.ts +60 -47
  401. package/src/__tests__/slash-commands-catalog.test.ts +37 -31
  402. package/src/__tests__/slash-commands-parser.test.ts +71 -64
  403. package/src/__tests__/slash-commands-resolver.test.ts +143 -107
  404. package/src/__tests__/slash-commands-rewrite.test.ts +22 -22
  405. package/src/__tests__/sms-messaging-provider.test.ts +4 -0
  406. package/src/__tests__/speaker-identification.test.ts +28 -25
  407. package/src/__tests__/starter-bundle.test.ts +27 -23
  408. package/src/__tests__/starter-task-flow.test.ts +67 -52
  409. package/src/__tests__/subagent-manager-notify.test.ts +154 -108
  410. package/src/__tests__/subagent-tools.test.ts +311 -270
  411. package/src/__tests__/subagent-types.test.ts +40 -40
  412. package/src/__tests__/surface-mutex-cleanup.test.ts +42 -30
  413. package/src/__tests__/swarm-dag-pathological.test.ts +122 -111
  414. package/src/__tests__/swarm-orchestrator.test.ts +135 -101
  415. package/src/__tests__/swarm-plan-validator.test.ts +125 -73
  416. package/src/__tests__/swarm-recursion.test.ts +58 -46
  417. package/src/__tests__/swarm-router-planner.test.ts +99 -74
  418. package/src/__tests__/swarm-session-integration.test.ts +148 -91
  419. package/src/__tests__/swarm-tool.test.ts +65 -45
  420. package/src/__tests__/swarm-worker-backend.test.ts +59 -45
  421. package/src/__tests__/swarm-worker-runner.test.ts +133 -118
  422. package/src/__tests__/system-prompt.test.ts +311 -256
  423. package/src/__tests__/task-compiler.test.ts +176 -120
  424. package/src/__tests__/task-management-tools.test.ts +561 -456
  425. package/src/__tests__/task-memory-cleanup.test.ts +627 -362
  426. package/src/__tests__/task-runner.test.ts +117 -94
  427. package/src/__tests__/task-scheduler.test.ts +113 -84
  428. package/src/__tests__/task-tools.test.ts +349 -264
  429. package/src/__tests__/terminal-sandbox.test.ts +138 -108
  430. package/src/__tests__/terminal-tools.test.ts +350 -305
  431. package/src/__tests__/thread-seed-composer.test.ts +307 -180
  432. package/src/__tests__/tool-approval-handler.test.ts +238 -137
  433. package/src/__tests__/tool-audit-listener.test.ts +69 -69
  434. package/src/__tests__/tool-domain-event-publisher.test.ts +142 -132
  435. package/src/__tests__/tool-execution-abort-cleanup.test.ts +155 -146
  436. package/src/__tests__/tool-execution-pipeline.benchmark.test.ts +136 -105
  437. package/src/__tests__/tool-executor-lifecycle-events.test.ts +355 -239
  438. package/src/__tests__/tool-executor-redaction.test.ts +112 -109
  439. package/src/__tests__/tool-executor-shell-integration.test.ts +130 -79
  440. package/src/__tests__/tool-executor.test.ts +1274 -674
  441. package/src/__tests__/tool-grant-request-escalation.test.ts +401 -283
  442. package/src/__tests__/tool-metrics-listener.test.ts +97 -85
  443. package/src/__tests__/tool-notification-listener.test.ts +42 -25
  444. package/src/__tests__/tool-permission-simulate-handler.test.ts +137 -113
  445. package/src/__tests__/tool-policy.test.ts +44 -25
  446. package/src/__tests__/tool-profiling-listener.test.ts +99 -93
  447. package/src/__tests__/tool-result-truncation.test.ts +5 -4
  448. package/src/__tests__/tool-trace-listener.test.ts +131 -111
  449. package/src/__tests__/top-level-renderer.test.ts +62 -58
  450. package/src/__tests__/top-level-scanner.test.ts +68 -64
  451. package/src/__tests__/trace-emitter.test.ts +56 -56
  452. package/src/__tests__/trust-context-guards.test.ts +65 -65
  453. package/src/__tests__/trust-store.test.ts +1239 -806
  454. package/src/__tests__/trusted-contact-approval-notifier.test.ts +0 -1
  455. package/src/__tests__/trusted-contact-inline-approval-integration.test.ts +0 -1
  456. package/src/__tests__/trusted-contact-lifecycle-notifications.test.ts +3 -2
  457. package/src/__tests__/trusted-contact-multichannel.test.ts +3 -2
  458. package/src/__tests__/trusted-contact-verification.test.ts +251 -231
  459. package/src/__tests__/turn-commit.test.ts +259 -200
  460. package/src/__tests__/twilio-provider.test.ts +140 -126
  461. package/src/__tests__/twilio-rest.test.ts +22 -18
  462. package/src/__tests__/twilio-routes-elevenlabs.test.ts +0 -1
  463. package/src/__tests__/twilio-routes-twiml.test.ts +55 -55
  464. package/src/__tests__/twilio-routes.test.ts +0 -1
  465. package/src/__tests__/twitter-auth-handler.test.ts +184 -139
  466. package/src/__tests__/twitter-cli-error-shaping.test.ts +88 -73
  467. package/src/__tests__/twitter-cli-routing.test.ts +146 -99
  468. package/src/__tests__/twitter-oauth-client.test.ts +82 -65
  469. package/src/__tests__/update-bulletin-format.test.ts +69 -66
  470. package/src/__tests__/update-bulletin-state.test.ts +66 -60
  471. package/src/__tests__/update-bulletin.test.ts +150 -114
  472. package/src/__tests__/update-template-contract.test.ts +15 -10
  473. package/src/__tests__/url-safety.test.ts +288 -265
  474. package/src/__tests__/user-reference.test.ts +32 -32
  475. package/src/__tests__/view-image-tool.test.ts +118 -96
  476. package/src/__tests__/voice-invite-redemption.test.ts +111 -106
  477. package/src/__tests__/voice-quality.test.ts +117 -102
  478. package/src/__tests__/voice-scoped-grant-consumer.test.ts +204 -146
  479. package/src/__tests__/voice-session-bridge.test.ts +351 -216
  480. package/src/__tests__/weather-skill-regression.test.ts +170 -120
  481. package/src/__tests__/web-fetch.test.ts +664 -526
  482. package/src/__tests__/web-search.test.ts +379 -213
  483. package/src/__tests__/work-item-output.test.ts +90 -53
  484. package/src/__tests__/workspace-git-service.test.ts +437 -356
  485. package/src/__tests__/workspace-heartbeat-service.test.ts +125 -91
  486. package/src/__tests__/workspace-lifecycle.test.ts +98 -64
  487. package/src/__tests__/workspace-policy.test.ts +139 -71
  488. package/src/cli/mcp.ts +81 -28
  489. package/src/commands/__tests__/cc-command-registry.test.ts +142 -134
  490. package/src/config/__tests__/feature-flag-registry-guard.test.ts +48 -39
  491. package/src/config/bundled-skills/chatgpt-import/tools/chatgpt-import.ts +25 -10
  492. package/src/config/bundled-skills/doordash/__tests__/doordash-session.test.ts +0 -1
  493. package/src/config/bundled-skills/guardian-verify-setup/SKILL.md +6 -11
  494. package/src/config/bundled-skills/messaging/SKILL.md +4 -3
  495. package/src/config/bundled-skills/messaging/tools/gmail-outreach-scan.ts +15 -5
  496. package/src/config/bundled-skills/messaging/tools/gmail-sender-digest.ts +16 -5
  497. package/src/config/bundled-skills/phone-calls/SKILL.md +1 -2
  498. package/src/config/bundled-skills/slack/tools/slack-scan-digest.ts +34 -32
  499. package/src/config/bundled-skills/sms-setup/SKILL.md +8 -16
  500. package/src/config/bundled-skills/telegram-setup/SKILL.md +3 -3
  501. package/src/config/bundled-skills/trusted-contacts/SKILL.md +13 -25
  502. package/src/config/bundled-skills/twilio-setup/SKILL.md +13 -23
  503. package/src/config/bundled-tool-registry.ts +2 -0
  504. package/src/config/env.ts +3 -4
  505. package/src/config/system-prompt.ts +32 -0
  506. package/src/mcp/client.ts +2 -7
  507. package/src/memory/db-connection.ts +16 -10
  508. package/src/messaging/providers/gmail/adapter.ts +10 -3
  509. package/src/messaging/providers/gmail/client.ts +280 -72
  510. package/src/runtime/auth/__tests__/context.test.ts +75 -65
  511. package/src/runtime/auth/__tests__/credential-service.test.ts +137 -114
  512. package/src/runtime/auth/__tests__/guard-tests.test.ts +84 -90
  513. package/src/runtime/auth/__tests__/ipc-auth-context.test.ts +40 -40
  514. package/src/runtime/auth/__tests__/middleware.test.ts +80 -74
  515. package/src/runtime/auth/__tests__/policy.test.ts +9 -9
  516. package/src/runtime/auth/__tests__/route-policy.test.ts +76 -65
  517. package/src/runtime/auth/__tests__/scopes.test.ts +68 -60
  518. package/src/runtime/auth/__tests__/subject.test.ts +54 -54
  519. package/src/runtime/auth/__tests__/token-service.test.ts +115 -108
  520. package/src/runtime/auth/scopes.ts +3 -0
  521. package/src/runtime/auth/token-service.ts +4 -1
  522. package/src/runtime/auth/types.ts +2 -1
  523. package/src/runtime/http-server.ts +2 -1
  524. package/src/security/secure-keys.ts +120 -54
  525. package/src/tools/browser/__tests__/auth-cache.test.ts +69 -63
  526. package/src/tools/browser/__tests__/auth-detector.test.ts +218 -157
  527. package/src/tools/browser/__tests__/jit-auth.test.ts +83 -99
  528. package/src/tools/terminal/safe-env.ts +7 -0
@@ -1,43 +1,51 @@
1
- import { mkdirSync, rmSync } from 'node:fs';
2
- import { tmpdir } from 'node:os';
3
- import { join } from 'node:path';
4
-
5
- import { afterAll, afterEach, beforeAll, beforeEach, describe, expect, mock, test } from 'bun:test';
1
+ import { mkdirSync, rmSync } from "node:fs";
2
+ import { tmpdir } from "node:os";
3
+ import { join } from "node:path";
4
+ import {
5
+ afterAll,
6
+ afterEach,
7
+ beforeAll,
8
+ beforeEach,
9
+ describe,
10
+ expect,
11
+ mock,
12
+ test,
13
+ } from "bun:test";
6
14
 
7
15
  // ---------------------------------------------------------------------------
8
16
  // Temp directory scaffold
9
17
  // ---------------------------------------------------------------------------
10
18
 
11
19
  const TEST_DIR = join(tmpdir(), `config-watcher-test-${crypto.randomUUID()}`);
12
- const WORKSPACE_DIR = join(TEST_DIR, 'workspace');
13
- const PROTECTED_DIR = join(TEST_DIR, 'protected');
14
- const SKILLS_DIR = join(WORKSPACE_DIR, 'skills');
20
+ const WORKSPACE_DIR = join(TEST_DIR, "workspace");
21
+ const PROTECTED_DIR = join(TEST_DIR, "protected");
22
+ const SKILLS_DIR = join(WORKSPACE_DIR, "skills");
15
23
 
16
24
  // ---------------------------------------------------------------------------
17
25
  // Mock platform paths
18
26
  // ---------------------------------------------------------------------------
19
27
 
20
- mock.module('../util/platform.js', () => ({
28
+ mock.module("../util/platform.js", () => ({
21
29
  getRootDir: () => TEST_DIR,
22
30
  getWorkspaceDir: () => WORKSPACE_DIR,
23
31
  getWorkspaceSkillsDir: () => SKILLS_DIR,
24
- getWorkspaceConfigPath: () => join(WORKSPACE_DIR, 'config.json'),
32
+ getWorkspaceConfigPath: () => join(WORKSPACE_DIR, "config.json"),
25
33
  getWorkspacePromptPath: (file: string) => join(WORKSPACE_DIR, file),
26
34
  ensureDataDir: () => {},
27
- getDataDir: () => join(WORKSPACE_DIR, 'data'),
28
- getSocketPath: () => join(TEST_DIR, 'vellum.sock'),
29
- getPidPath: () => join(TEST_DIR, 'vellum.pid'),
30
- getDbPath: () => join(WORKSPACE_DIR, 'data', 'assistant.db'),
31
- getLogPath: () => join(WORKSPACE_DIR, 'data', 'logs', 'vellum.log'),
32
- getHistoryPath: () => join(WORKSPACE_DIR, 'data', 'history'),
33
- getHooksDir: () => join(WORKSPACE_DIR, 'hooks'),
34
- getIpcBlobDir: () => join(WORKSPACE_DIR, 'data', 'ipc-blobs'),
35
- getSandboxRootDir: () => join(WORKSPACE_DIR, 'data', 'sandbox'),
35
+ getDataDir: () => join(WORKSPACE_DIR, "data"),
36
+ getSocketPath: () => join(TEST_DIR, "vellum.sock"),
37
+ getPidPath: () => join(TEST_DIR, "vellum.pid"),
38
+ getDbPath: () => join(WORKSPACE_DIR, "data", "assistant.db"),
39
+ getLogPath: () => join(WORKSPACE_DIR, "data", "logs", "vellum.log"),
40
+ getHistoryPath: () => join(WORKSPACE_DIR, "data", "history"),
41
+ getHooksDir: () => join(WORKSPACE_DIR, "hooks"),
42
+ getIpcBlobDir: () => join(WORKSPACE_DIR, "data", "ipc-blobs"),
43
+ getSandboxRootDir: () => join(WORKSPACE_DIR, "data", "sandbox"),
36
44
  getSandboxWorkingDir: () => WORKSPACE_DIR,
37
- getInterfacesDir: () => join(WORKSPACE_DIR, 'data', 'interfaces'),
38
- isMacOS: () => process.platform === 'darwin',
39
- isLinux: () => process.platform === 'linux',
40
- isWindows: () => process.platform === 'win32',
45
+ getInterfacesDir: () => join(WORKSPACE_DIR, "data", "interfaces"),
46
+ isMacOS: () => process.platform === "darwin",
47
+ isLinux: () => process.platform === "linux",
48
+ isWindows: () => process.platform === "win32",
41
49
  getPlatformName: () => process.platform,
42
50
  getClipboardCommand: () => null,
43
51
  removeSocketFile: () => {},
@@ -46,10 +54,11 @@ mock.module('../util/platform.js', () => ({
46
54
  migrateToDataLayout: () => {},
47
55
  }));
48
56
 
49
- mock.module('../util/logger.js', () => ({
50
- getLogger: () => new Proxy({} as Record<string, unknown>, {
51
- get: () => () => {},
52
- }),
57
+ mock.module("../util/logger.js", () => ({
58
+ getLogger: () =>
59
+ new Proxy({} as Record<string, unknown>, {
60
+ get: () => () => {},
61
+ }),
53
62
  isDebug: () => false,
54
63
  truncateForLog: (v: string) => v,
55
64
  }));
@@ -72,16 +81,16 @@ const fakeWatcher = {
72
81
  close: () => {},
73
82
  };
74
83
 
75
- mock.module('node:fs', () => {
84
+ mock.module("node:fs", () => {
76
85
  // eslint-disable-next-line @typescript-eslint/no-require-imports
77
- const actual = require('node:fs');
86
+ const actual = require("node:fs");
78
87
  return {
79
88
  ...actual,
80
89
  watch: (dir: string, ...args: unknown[]) => {
81
90
  let callback: WatchCallback;
82
91
  let options: { recursive?: boolean } | undefined;
83
92
 
84
- if (typeof args[0] === 'function') {
93
+ if (typeof args[0] === "function") {
85
94
  callback = args[0] as WatchCallback;
86
95
  } else {
87
96
  options = args[0] as { recursive?: boolean };
@@ -95,34 +104,38 @@ mock.module('node:fs', () => {
95
104
  });
96
105
 
97
106
  // Mock config/loader and other dependencies that ConfigWatcher imports
98
- mock.module('../config/loader.js', () => ({
107
+ mock.module("../config/loader.js", () => ({
99
108
  getConfig: () => ({
100
109
  ui: {},
101
- }),
110
+ }),
102
111
  invalidateConfigCache: () => {},
103
112
  }));
104
113
 
105
- mock.module('../memory/embedding-backend.js', () => ({
114
+ mock.module("../memory/embedding-backend.js", () => ({
106
115
  clearEmbeddingBackendCache: () => {},
107
116
  }));
108
117
 
109
118
  let trustClearCacheCallCount = 0;
110
- mock.module('../permissions/trust-store.js', () => ({
111
- clearCache: () => { trustClearCacheCallCount++; },
119
+ mock.module("../permissions/trust-store.js", () => ({
120
+ clearCache: () => {
121
+ trustClearCacheCallCount++;
122
+ },
112
123
  }));
113
124
 
114
- mock.module('../providers/registry.js', () => ({
125
+ mock.module("../providers/registry.js", () => ({
115
126
  initializeProviders: () => {},
116
127
  }));
117
128
 
118
129
  let resetAllowlistCallCount = 0;
119
- mock.module('../security/secret-allowlist.js', () => ({
120
- resetAllowlist: () => { resetAllowlistCallCount++; },
130
+ mock.module("../security/secret-allowlist.js", () => ({
131
+ resetAllowlist: () => {
132
+ resetAllowlistCallCount++;
133
+ },
121
134
  validateAllowlistFile: () => [],
122
135
  }));
123
136
 
124
137
  // Import after mocks are set up
125
- const { ConfigWatcher } = await import('../daemon/config-watcher.js');
138
+ const { ConfigWatcher } = await import("../daemon/config-watcher.js");
126
139
 
127
140
  // ---------------------------------------------------------------------------
128
141
  // Helpers
@@ -137,7 +150,7 @@ function findWatcher(dir: string): CapturedWatcher | undefined {
137
150
  function simulateFileChange(dir: string, filename: string): void {
138
151
  const watcher = findWatcher(dir);
139
152
  if (!watcher) throw new Error(`No watcher found for ${dir}`);
140
- watcher.callback('change', filename);
153
+ watcher.callback("change", filename);
141
154
  }
142
155
 
143
156
  // ---------------------------------------------------------------------------
@@ -155,7 +168,9 @@ afterAll(() => {
155
168
 
156
169
  let watcher: InstanceType<typeof ConfigWatcher>;
157
170
  let evictCallCount: number;
158
- const onSessionEvict = () => { evictCallCount++; };
171
+ const onSessionEvict = () => {
172
+ evictCallCount++;
173
+ };
159
174
 
160
175
  beforeEach(() => {
161
176
  capturedWatchers.length = 0;
@@ -169,41 +184,41 @@ afterEach(() => {
169
184
  watcher.stop();
170
185
  });
171
186
 
172
- describe('ConfigWatcher workspace file handlers', () => {
173
- test('SOUL.md change triggers onSessionEvict', async () => {
187
+ describe("ConfigWatcher workspace file handlers", () => {
188
+ test("SOUL.md change triggers onSessionEvict", async () => {
174
189
  watcher.start(onSessionEvict);
175
- simulateFileChange(WORKSPACE_DIR, 'SOUL.md');
190
+ simulateFileChange(WORKSPACE_DIR, "SOUL.md");
176
191
 
177
192
  // Wait for the debounce timer to fire (default 200ms)
178
193
  await new Promise((r) => setTimeout(r, 300));
179
194
  expect(evictCallCount).toBe(1);
180
195
  });
181
196
 
182
- test('IDENTITY.md change triggers onSessionEvict', async () => {
197
+ test("IDENTITY.md change triggers onSessionEvict", async () => {
183
198
  watcher.start(onSessionEvict);
184
- simulateFileChange(WORKSPACE_DIR, 'IDENTITY.md');
199
+ simulateFileChange(WORKSPACE_DIR, "IDENTITY.md");
185
200
 
186
201
  await new Promise((r) => setTimeout(r, 300));
187
202
  expect(evictCallCount).toBe(1);
188
203
  });
189
204
 
190
- test('USER.md change triggers onSessionEvict', async () => {
205
+ test("USER.md change triggers onSessionEvict", async () => {
191
206
  watcher.start(onSessionEvict);
192
- simulateFileChange(WORKSPACE_DIR, 'USER.md');
207
+ simulateFileChange(WORKSPACE_DIR, "USER.md");
193
208
 
194
209
  await new Promise((r) => setTimeout(r, 300));
195
210
  expect(evictCallCount).toBe(1);
196
211
  });
197
212
 
198
- test('UPDATES.md change triggers onSessionEvict', async () => {
213
+ test("UPDATES.md change triggers onSessionEvict", async () => {
199
214
  watcher.start(onSessionEvict);
200
- simulateFileChange(WORKSPACE_DIR, 'UPDATES.md');
215
+ simulateFileChange(WORKSPACE_DIR, "UPDATES.md");
201
216
 
202
217
  await new Promise((r) => setTimeout(r, 300));
203
218
  expect(evictCallCount).toBe(1);
204
219
  });
205
220
 
206
- test('config.json change calls refreshConfigFromSources', async () => {
221
+ test("config.json change calls refreshConfigFromSources", async () => {
207
222
  let refreshCalled = false;
208
223
  watcher.refreshConfigFromSources = () => {
209
224
  refreshCalled = true;
@@ -211,7 +226,7 @@ describe('ConfigWatcher workspace file handlers', () => {
211
226
  };
212
227
 
213
228
  watcher.start(onSessionEvict);
214
- simulateFileChange(WORKSPACE_DIR, 'config.json');
229
+ simulateFileChange(WORKSPACE_DIR, "config.json");
215
230
 
216
231
  await new Promise((r) => setTimeout(r, 300));
217
232
  expect(refreshCalled).toBe(true);
@@ -219,17 +234,17 @@ describe('ConfigWatcher workspace file handlers', () => {
219
234
  expect(evictCallCount).toBe(0);
220
235
  });
221
236
 
222
- test('config.json change triggers onSessionEvict when config actually changed', async () => {
237
+ test("config.json change triggers onSessionEvict when config actually changed", async () => {
223
238
  watcher.refreshConfigFromSources = () => true;
224
239
 
225
240
  watcher.start(onSessionEvict);
226
- simulateFileChange(WORKSPACE_DIR, 'config.json');
241
+ simulateFileChange(WORKSPACE_DIR, "config.json");
227
242
 
228
243
  await new Promise((r) => setTimeout(r, 300));
229
244
  expect(evictCallCount).toBe(1);
230
245
  });
231
246
 
232
- test('config.json change is suppressed when suppressConfigReload is true', async () => {
247
+ test("config.json change is suppressed when suppressConfigReload is true", async () => {
233
248
  let refreshCalled = false;
234
249
  watcher.refreshConfigFromSources = () => {
235
250
  refreshCalled = true;
@@ -238,38 +253,38 @@ describe('ConfigWatcher workspace file handlers', () => {
238
253
 
239
254
  watcher.suppressConfigReload = true;
240
255
  watcher.start(onSessionEvict);
241
- simulateFileChange(WORKSPACE_DIR, 'config.json');
256
+ simulateFileChange(WORKSPACE_DIR, "config.json");
242
257
 
243
258
  await new Promise((r) => setTimeout(r, 300));
244
259
  expect(refreshCalled).toBe(false);
245
260
  expect(evictCallCount).toBe(0);
246
261
  });
247
262
 
248
- test('unknown file does not trigger any handler', async () => {
263
+ test("unknown file does not trigger any handler", async () => {
249
264
  watcher.start(onSessionEvict);
250
- simulateFileChange(WORKSPACE_DIR, 'UNKNOWN.md');
265
+ simulateFileChange(WORKSPACE_DIR, "UNKNOWN.md");
251
266
 
252
267
  await new Promise((r) => setTimeout(r, 300));
253
268
  expect(evictCallCount).toBe(0);
254
269
  });
255
270
 
256
- test('null filename does not trigger any handler', async () => {
271
+ test("null filename does not trigger any handler", async () => {
257
272
  watcher.start(onSessionEvict);
258
273
  const wsWatcher = findWatcher(WORKSPACE_DIR);
259
274
  expect(wsWatcher).toBeDefined();
260
- wsWatcher!.callback('change', null);
275
+ wsWatcher!.callback("change", null);
261
276
 
262
277
  await new Promise((r) => setTimeout(r, 300));
263
278
  expect(evictCallCount).toBe(0);
264
279
  });
265
280
  });
266
281
 
267
- describe('ConfigWatcher protected directory handlers', () => {
268
- test('trust.json change calls clearTrustCache', async () => {
282
+ describe("ConfigWatcher protected directory handlers", () => {
283
+ test("trust.json change calls clearTrustCache", async () => {
269
284
  watcher.start(onSessionEvict);
270
285
  const protectedWatcher = findWatcher(PROTECTED_DIR);
271
286
  expect(protectedWatcher).toBeDefined();
272
- protectedWatcher!.callback('change', 'trust.json');
287
+ protectedWatcher!.callback("change", "trust.json");
273
288
 
274
289
  await new Promise((r) => setTimeout(r, 300));
275
290
  // trust.json should NOT trigger session eviction
@@ -278,11 +293,11 @@ describe('ConfigWatcher protected directory handlers', () => {
278
293
  expect(trustClearCacheCallCount).toBe(1);
279
294
  });
280
295
 
281
- test('secret-allowlist.json change calls resetAllowlist', async () => {
296
+ test("secret-allowlist.json change calls resetAllowlist", async () => {
282
297
  watcher.start(onSessionEvict);
283
298
  const protectedWatcher = findWatcher(PROTECTED_DIR);
284
299
  expect(protectedWatcher).toBeDefined();
285
- protectedWatcher!.callback('change', 'secret-allowlist.json');
300
+ protectedWatcher!.callback("change", "secret-allowlist.json");
286
301
 
287
302
  await new Promise((r) => setTimeout(r, 300));
288
303
  // secret-allowlist.json should NOT trigger session eviction
@@ -292,8 +307,8 @@ describe('ConfigWatcher protected directory handlers', () => {
292
307
  });
293
308
  });
294
309
 
295
- describe('ConfigWatcher watcher lifecycle', () => {
296
- test('start registers watchers for workspace and protected dirs', () => {
310
+ describe("ConfigWatcher watcher lifecycle", () => {
311
+ test("start registers watchers for workspace and protected dirs", () => {
297
312
  watcher.start(onSessionEvict);
298
313
  const wsWatcher = findWatcher(WORKSPACE_DIR);
299
314
  const protWatcher = findWatcher(PROTECTED_DIR);
@@ -301,34 +316,34 @@ describe('ConfigWatcher watcher lifecycle', () => {
301
316
  expect(protWatcher).toBeDefined();
302
317
  });
303
318
 
304
- test('stop cancels all debounce timers and clears watchers', () => {
319
+ test("stop cancels all debounce timers and clears watchers", () => {
305
320
  watcher.start(onSessionEvict);
306
321
  // Trigger a file change but don't wait for the debounce
307
- simulateFileChange(WORKSPACE_DIR, 'SOUL.md');
322
+ simulateFileChange(WORKSPACE_DIR, "SOUL.md");
308
323
  watcher.stop();
309
324
 
310
325
  // The debounce should have been cancelled, so no eviction
311
326
  expect(evictCallCount).toBe(0);
312
327
  });
313
328
 
314
- test('multiple prompt file changes are debounced', async () => {
329
+ test("multiple prompt file changes are debounced", async () => {
315
330
  watcher.start(onSessionEvict);
316
331
 
317
332
  // Rapid fire multiple changes to the same file
318
- simulateFileChange(WORKSPACE_DIR, 'SOUL.md');
319
- simulateFileChange(WORKSPACE_DIR, 'SOUL.md');
320
- simulateFileChange(WORKSPACE_DIR, 'SOUL.md');
333
+ simulateFileChange(WORKSPACE_DIR, "SOUL.md");
334
+ simulateFileChange(WORKSPACE_DIR, "SOUL.md");
335
+ simulateFileChange(WORKSPACE_DIR, "SOUL.md");
321
336
 
322
337
  await new Promise((r) => setTimeout(r, 300));
323
338
  // Despite 3 events, debouncing should collapse them to 1 call
324
339
  expect(evictCallCount).toBe(1);
325
340
  });
326
341
 
327
- test('changes to different files each trigger their own handler', async () => {
342
+ test("changes to different files each trigger their own handler", async () => {
328
343
  watcher.start(onSessionEvict);
329
344
 
330
- simulateFileChange(WORKSPACE_DIR, 'SOUL.md');
331
- simulateFileChange(WORKSPACE_DIR, 'IDENTITY.md');
345
+ simulateFileChange(WORKSPACE_DIR, "SOUL.md");
346
+ simulateFileChange(WORKSPACE_DIR, "IDENTITY.md");
332
347
 
333
348
  await new Promise((r) => setTimeout(r, 300));
334
349
  // Each file has its own debounce key, so both should fire
@@ -336,14 +351,14 @@ describe('ConfigWatcher watcher lifecycle', () => {
336
351
  });
337
352
  });
338
353
 
339
- describe('ConfigWatcher fingerprinting', () => {
340
- test('configFingerprint returns JSON string of config', () => {
341
- const config = { foo: 'bar' } as any;
354
+ describe("ConfigWatcher fingerprinting", () => {
355
+ test("configFingerprint returns JSON string of config", () => {
356
+ const config = { foo: "bar" } as any;
342
357
  expect(watcher.configFingerprint(config)).toBe(JSON.stringify(config));
343
358
  });
344
359
 
345
- test('initFingerprint sets lastFingerprint', () => {
346
- const config = { key: 'value' } as any;
360
+ test("initFingerprint sets lastFingerprint", () => {
361
+ const config = { key: "value" } as any;
347
362
  watcher.initFingerprint(config);
348
363
  expect(watcher.lastFingerprint).toBe(JSON.stringify(config));
349
364
  });