@vellumai/assistant 0.12.1-staging.1 → 0.12.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (404) hide show
  1. package/AGENTS.md +0 -4
  2. package/ARCHITECTURE.md +12 -11
  3. package/docs/architecture/turn-actor.md +8 -15
  4. package/openapi.yaml +1 -291
  5. package/package.json +1 -1
  6. package/src/__tests__/always-loaded-tools-guard.test.ts +10 -18
  7. package/src/__tests__/app-compiler.test.ts +0 -6
  8. package/src/__tests__/app-control-tool-schemas.test.ts +2 -5
  9. package/src/__tests__/app-dir-path-guard.test.ts +3 -1
  10. package/src/__tests__/app-source-watcher.test.ts +218 -0
  11. package/src/{calls/__tests__ → __tests__}/call-controller.test.ts +82 -503
  12. package/src/__tests__/computer-use-skill-proxy-bridge.test.ts +2 -5
  13. package/src/__tests__/computer-use-tools.test.ts +5 -17
  14. package/src/__tests__/config-schema-cmd.test.ts +2 -2
  15. package/src/__tests__/config-schema.test.ts +29 -28
  16. package/src/__tests__/config-watcher-skill-reseed.test.ts +359 -0
  17. package/src/__tests__/config-watcher.test.ts +8 -23
  18. package/src/__tests__/connection-model-compat.test.ts +2 -2
  19. package/src/__tests__/conversation-key-store-disk-view.test.ts +1 -1
  20. package/src/__tests__/conversation-pairing.test.ts +0 -26
  21. package/src/__tests__/conversation-process-app-control-preactivation.test.ts +10 -4
  22. package/src/__tests__/conversation-queue.test.ts +207 -48
  23. package/src/__tests__/conversation-retry-discard.test.ts +1 -54
  24. package/src/__tests__/conversation-skill-tools.test.ts +0 -27
  25. package/src/__tests__/conversation-surfaces-app-control.test.ts +3 -8
  26. package/src/__tests__/conversation-surfaces-task-progress.test.ts +0 -67
  27. package/src/__tests__/conversation-title-service.test.ts +10 -14
  28. package/src/__tests__/conversation-tool-setup-app-refresh.test.ts +5 -3
  29. package/src/__tests__/conversation-tool-setup-attribution.test.ts +0 -51
  30. package/src/__tests__/credential-record-retire.test.ts +1 -171
  31. package/src/__tests__/credential-routes.test.ts +3 -212
  32. package/src/__tests__/credential-security-invariants.test.ts +1 -2
  33. package/src/__tests__/cu-unified-flow.test.ts +2 -8
  34. package/src/__tests__/drain-kick-guard.test.ts +2 -0
  35. package/src/__tests__/drain-requeue-on-contention.test.ts +6 -0
  36. package/src/__tests__/evict-conversations-for-reload.test.ts +1 -1
  37. package/src/__tests__/host-bash-proxy.test.ts +45 -26
  38. package/src/__tests__/host-browser-proxy.test.ts +17 -6
  39. package/src/__tests__/host-file-proxy-targeted.test.ts +0 -23
  40. package/src/__tests__/host-file-proxy.test.ts +23 -11
  41. package/src/__tests__/host-transfer-proxy-targeted.test.ts +9 -30
  42. package/src/__tests__/llm-catalog-parity.test.ts +0 -25
  43. package/src/__tests__/mcp-auth-routes.test.ts +9 -6
  44. package/src/__tests__/mcp-config-secret-boundary.test.ts +136 -78
  45. package/src/__tests__/mcp-health-check.test.ts +11 -8
  46. package/src/__tests__/mcp-list-plugin-servers.test.ts +10 -8
  47. package/src/{calls/__tests__ → __tests__}/media-stream-audio-transcode.test.ts +1 -1
  48. package/src/{calls/__tests__ → __tests__}/media-stream-output.test.ts +8 -37
  49. package/src/{calls/__tests__ → __tests__}/media-stream-parser.test.ts +1 -1
  50. package/src/{calls/__tests__ → __tests__}/media-stream-server-integration.test.ts +57 -150
  51. package/src/{calls/__tests__ → __tests__}/media-stream-stt-session.test.ts +5 -5
  52. package/src/{calls/__tests__ → __tests__}/media-turn-detector.test.ts +1 -1
  53. package/src/__tests__/messages-after-tiebreaker.test.ts +0 -91
  54. package/src/__tests__/messages-read-boundary-guard.test.ts +1 -1
  55. package/src/__tests__/messaging-send-tool.test.ts +548 -355
  56. package/src/__tests__/model-intents.test.ts +0 -3
  57. package/src/__tests__/outlook-messaging-provider.test.ts +6 -6
  58. package/src/__tests__/platform-client-verify-credential.test.ts +0 -2
  59. package/src/__tests__/plugin-import-boundary-guard.test.ts +0 -13
  60. package/src/__tests__/script-proxy-certs.test.ts +0 -35
  61. package/src/__tests__/skill-feature-flags-integration.test.ts +1 -1
  62. package/src/__tests__/skill-feature-flags.test.ts +2 -2
  63. package/src/__tests__/speaker-identification.test.ts +56 -0
  64. package/src/__tests__/subagent-tool-gate-mode.test.ts +3 -19
  65. package/src/__tests__/subagent-tools.test.ts +2 -3
  66. package/src/__tests__/telephony-tts-guard.test.ts +3 -38
  67. package/src/__tests__/vellum-self-knowledge-inline-command.test.ts +0 -4
  68. package/src/{calls/__tests__/voice-session-bridge-turn-flow.test.ts → __tests__/voice-session-bridge.test.ts} +12 -20
  69. package/src/__tests__/watch-retro-tool-availability.test.ts +17 -8
  70. package/src/__tests__/workspace-git-service.test.ts +0 -26
  71. package/src/acp/__tests__/agent-process.test.ts +4 -258
  72. package/src/acp/__tests__/auth-required.test.ts +0 -96
  73. package/src/acp/__tests__/client-handler.test.ts +2 -90
  74. package/src/acp/__tests__/session-manager-persistence.test.ts +1 -5
  75. package/src/acp/__tests__/session-manager-resume.test.ts +6 -270
  76. package/src/acp/__tests__/session-manager-usage.test.ts +2 -4
  77. package/src/acp/__tests__/session-manager.test.ts +4 -895
  78. package/src/acp/agent-process.test.ts +1 -4
  79. package/src/acp/agent-process.ts +9 -94
  80. package/src/acp/auth-required.ts +1 -50
  81. package/src/acp/auto-install.test.ts +7 -9
  82. package/src/acp/client-handler.ts +3 -16
  83. package/src/acp/resolve-agent.test.ts +6 -220
  84. package/src/acp/resolve-agent.ts +23 -88
  85. package/src/acp/session-manager.test.ts +3 -196
  86. package/src/acp/session-manager.ts +18 -441
  87. package/src/acp/types.ts +5 -50
  88. package/src/api/events/app-files-changed.ts +3 -4
  89. package/src/api/index.ts +0 -6
  90. package/src/apps/app-store.ts +1 -1
  91. package/src/bundler/app-compiler.ts +0 -15
  92. package/src/calls/__tests__/voice-control-protocol.test.ts +25 -58
  93. package/src/calls/__tests__/voice-session-bridge.test.ts +1 -37
  94. package/src/calls/__tests__/voice-triage-escalate.test.ts +0 -105
  95. package/src/calls/call-constants.ts +4 -24
  96. package/src/calls/call-controller.ts +199 -499
  97. package/src/calls/call-transport.ts +0 -16
  98. package/src/calls/media-stream-output.ts +0 -32
  99. package/src/calls/media-stream-server.ts +30 -82
  100. package/src/calls/media-stream-stt-session.ts +0 -15
  101. package/src/calls/resolve-call-tts-provider.ts +2 -33
  102. package/src/calls/speaker-identification.ts +233 -0
  103. package/src/calls/tts-call-strategy.ts +5 -9
  104. package/src/calls/types.ts +0 -2
  105. package/src/calls/voice-control-protocol.ts +21 -53
  106. package/src/calls/voice-session-bridge.ts +46 -59
  107. package/src/calls/voice-triage-escalate.ts +56 -175
  108. package/src/cli/commands/apps.help.ts +13 -67
  109. package/src/cli/commands/apps.ts +0 -183
  110. package/src/cli/commands/channels/index.help.ts +2 -70
  111. package/src/cli/commands/channels/index.ts +3 -16
  112. package/src/cli/commands/credentials.help.ts +2 -6
  113. package/src/cli/commands/credentials.ts +2 -2
  114. package/src/cli/commands/mcp.help.ts +8 -8
  115. package/src/cli/commands/mcp.ts +1 -1
  116. package/src/cli/commands/roadmap.help.ts +1 -5
  117. package/src/cli/commands/roadmap.ts +1 -1
  118. package/src/cli/lib/bundled-marketplace.json +90 -103
  119. package/src/config/__tests__/default-profile-catalog.test.ts +0 -22
  120. package/src/config/__tests__/memory-retrospective-schema.test.ts +1 -15
  121. package/src/config/__tests__/platform-rehydration.test.ts +0 -93
  122. package/src/config/acp-defaults.test.ts +3 -13
  123. package/src/config/acp-defaults.ts +6 -23
  124. package/src/config/acp-schema.ts +2 -30
  125. package/src/config/bundled-skills/acp/SKILL.md +14 -22
  126. package/src/config/bundled-skills/acp/TOOLS.json +1 -5
  127. package/src/config/bundled-skills/app-builder/SKILL.md +9 -12
  128. package/src/config/bundled-skills/app-builder/references/CUSTOM_ROUTES.md +1 -1
  129. package/src/config/bundled-skills/messaging/TOOLS.json +3 -3
  130. package/src/config/bundled-skills/messaging/tools/messaging-send.ts +139 -67
  131. package/src/config/bundled-skills/phone-calls/references/TRANSCRIPTS.md +1 -1
  132. package/src/config/bundled-skills/screen-annotation/SKILL.md +1 -8
  133. package/src/config/bundled-skills/screen-annotation/tools/screen-annotation.test.ts +1 -4
  134. package/src/config/bundled-skills/skill-management/TOOLS.json +2 -2
  135. package/src/config/default-profile-catalog.ts +1 -1
  136. package/src/config/env.ts +2 -2
  137. package/src/config/feature-flag-registry.json +12 -8
  138. package/src/config/memory-v3-gate.test.ts +0 -31
  139. package/src/config/memory-v3-gate.ts +16 -20
  140. package/src/config/platform-rehydration.ts +21 -75
  141. package/src/config/schema.ts +2 -2
  142. package/src/config/schemas/__tests__/live-voice.test.ts +158 -8
  143. package/src/config/schemas/calls.ts +28 -1
  144. package/src/config/schemas/live-voice.ts +173 -1
  145. package/src/config/schemas/mcp.ts +1 -1
  146. package/src/config/schemas/memory-retrospective.ts +0 -10
  147. package/src/config/schemas/skills.ts +14 -0
  148. package/src/credential-execution/process-manager.test.ts +19 -18
  149. package/src/daemon/__tests__/conversation-tool-setup.test.ts +121 -66
  150. package/src/daemon/__tests__/plugin-mcp-reconcile.test.ts +1 -4
  151. package/src/daemon/app-source-watcher.ts +218 -0
  152. package/src/daemon/config-watcher.ts +194 -13
  153. package/src/daemon/conversation-process.ts +64 -35
  154. package/src/daemon/conversation-skill-tools.ts +31 -13
  155. package/src/daemon/conversation-store.ts +1 -1
  156. package/src/daemon/conversation-surfaces.ts +8 -10
  157. package/src/daemon/conversation-tool-setup.ts +43 -37
  158. package/src/daemon/conversation.ts +3 -0
  159. package/src/daemon/host-bash-proxy.ts +12 -8
  160. package/src/daemon/host-browser-proxy.ts +1 -15
  161. package/src/daemon/host-file-proxy.ts +10 -8
  162. package/src/daemon/host-transfer-proxy.ts +18 -14
  163. package/src/daemon/lifecycle.ts +5 -0
  164. package/src/daemon/mcp-reload-service.ts +5 -5
  165. package/src/daemon/message-types/sync.ts +0 -1
  166. package/src/daemon/providers-setup.ts +1 -1
  167. package/src/daemon/shutdown-handlers.ts +9 -1
  168. package/src/daemon/skill-memory-refresh.ts +0 -64
  169. package/src/daemon/tool-side-effects.ts +18 -7
  170. package/src/hooks/types.ts +0 -33
  171. package/src/inbound/platform-callback-registration.ts +5 -4
  172. package/src/live-voice/__tests__/live-voice-metrics.test.ts +3 -0
  173. package/src/live-voice/__tests__/live-voice-progress.test.ts +15 -15
  174. package/src/live-voice/__tests__/live-voice-vad.test.ts +2 -2
  175. package/src/{calls → live-voice}/__tests__/progress-narration.test.ts +4 -4
  176. package/src/{calls → live-voice}/__tests__/progress-phrases.test.ts +1 -1
  177. package/src/live-voice/__tests__/runtime-websocket-shell.test.ts +69 -13
  178. package/src/live-voice/live-voice-session.ts +693 -213
  179. package/src/{calls → live-voice}/progress-narration.ts +2 -2
  180. package/src/live-voice/protocol.ts +2 -0
  181. package/src/mcp/__tests__/effective-config.test.ts +2 -2
  182. package/src/mcp/effective-config.ts +3 -3
  183. package/src/mcp/mcp-header-store.ts +45 -29
  184. package/src/mcp/startup.ts +4 -8
  185. package/src/messaging/provider.ts +3 -10
  186. package/src/messaging/providers/callback-routing.ts +0 -18
  187. package/src/messaging/providers/channel-transport.ts +0 -56
  188. package/src/messaging/providers/discord/transport.ts +0 -17
  189. package/src/messaging/providers/slack/__tests__/adapter-token-routing.test.ts +17 -6
  190. package/src/messaging/providers/slack/adapter.ts +44 -7
  191. package/src/messaging/providers/slack/transport.ts +0 -16
  192. package/src/messaging/providers/telegram-bot/adapter.ts +48 -1
  193. package/src/messaging/providers/telegram-bot/client.ts +26 -0
  194. package/src/messaging/providers/telegram-bot/transport.ts +0 -20
  195. package/src/messaging/providers/whatsapp/adapter.ts +48 -1
  196. package/src/messaging/providers/whatsapp/client.ts +29 -0
  197. package/src/messaging/providers/whatsapp/transport.ts +0 -18
  198. package/src/monitoring/__tests__/workspace-git-heartbeat.test.ts +0 -8
  199. package/src/notifications/__tests__/assistant-reply-producer.test.ts +0 -55
  200. package/src/notifications/__tests__/home-feed-side-effect.test.ts +3 -153
  201. package/src/notifications/assistant-reply-producer.ts +3 -8
  202. package/src/notifications/conversation-pairing.ts +16 -36
  203. package/src/notifications/delivered-post-record.ts +1 -11
  204. package/src/notifications/home-feed-side-effect.ts +7 -55
  205. package/src/outbound-proxy/certs.ts +5 -3
  206. package/src/permissions/checker.test.ts +6 -11
  207. package/src/persistence/compaction-log-store-clickhouse.ts +3 -3
  208. package/src/persistence/conversation-crud.ts +63 -71
  209. package/src/persistence/conversation-lineage.ts +4 -12
  210. package/src/persistence/conversation-title-service.ts +26 -9
  211. package/src/persistence/llm-request-log-sink-clickhouse.ts +3 -3
  212. package/src/persistence/llm-request-log-source-clickhouse.ts +3 -3
  213. package/src/persistence/message-reads.ts +0 -30
  214. package/src/persistence/migrations/157-invite-contact-id.ts +6 -18
  215. package/src/persistence/schema/memory-core.ts +0 -5
  216. package/src/platform/client.test.ts +0 -2
  217. package/src/platform/client.ts +10 -2
  218. package/src/plugin-api/constants.ts +0 -2
  219. package/src/plugin-api/index.ts +0 -1
  220. package/src/plugin-api/types.ts +0 -2
  221. package/src/plugins/defaults/index.ts +0 -2
  222. package/src/plugins/defaults/memory/__tests__/memory-retrospective-accounting.test.ts +0 -46
  223. package/src/plugins/defaults/memory/__tests__/memory-retrospective-enqueue.test.ts +5 -9
  224. package/src/plugins/defaults/memory/__tests__/memory-retrospective-job.test.ts +10 -20
  225. package/src/plugins/defaults/memory/__tests__/memory-retrospective-state.test.ts +0 -219
  226. package/src/plugins/defaults/memory/__tests__/memory-retrospective-sweep.test.ts +0 -31
  227. package/src/plugins/defaults/memory/__tests__/memory-retrospective-trigger-check.test.ts +0 -63
  228. package/src/plugins/defaults/memory/__tests__/shutdown-hook.test.ts +0 -4
  229. package/src/plugins/defaults/memory/graph/capability-seed.ts +6 -4
  230. package/src/plugins/defaults/memory/hooks/init.ts +0 -10
  231. package/src/plugins/defaults/memory/hooks/shutdown.ts +0 -2
  232. package/src/plugins/defaults/memory/jobs-worker.ts +0 -13
  233. package/src/plugins/defaults/memory/memory-retrospective-accounting.ts +60 -34
  234. package/src/plugins/defaults/memory/memory-retrospective-enqueue.ts +5 -3
  235. package/src/plugins/defaults/memory/memory-retrospective-job.ts +3 -12
  236. package/src/plugins/defaults/memory/memory-retrospective-state.ts +71 -312
  237. package/src/plugins/defaults/memory/memory-retrospective-sweep.ts +1 -2
  238. package/src/plugins/defaults/memory/memory-retrospective-trigger-check.ts +3 -5
  239. package/src/plugins/defaults/memory/startup.ts +1 -6
  240. package/src/plugins/defaults/memory/substrate/__tests__/skill-content.test.ts +9 -7
  241. package/src/plugins/defaults/memory/substrate/skill-content.ts +2 -2
  242. package/src/plugins/defaults/memory/v3/__tests__/pool-select.test.ts +0 -89
  243. package/src/plugins/defaults/memory/worker.ts +0 -6
  244. package/src/plugins/mcp-servers.ts +75 -15
  245. package/src/providers/__tests__/connection-model-compat.test.ts +3 -3
  246. package/src/providers/gemini/client.ts +23 -9
  247. package/src/providers/model-catalog.ts +0 -34
  248. package/src/providers/model-intents.ts +5 -10
  249. package/src/providers/openai/__tests__/chat-completions-provider-reasoning.test.ts +18 -146
  250. package/src/providers/openai/__tests__/tool-choice-mapping.test.ts +1 -83
  251. package/src/providers/openai/chat-completions-provider.ts +78 -192
  252. package/src/providers/openai/codex-models.ts +4 -0
  253. package/src/runtime/AGENTS.md +0 -2
  254. package/src/runtime/auth/same-actor.ts +3 -38
  255. package/src/runtime/http-server.ts +151 -160
  256. package/src/runtime/routes/__tests__/acp-routes.test.ts +4 -159
  257. package/src/runtime/routes/__tests__/conversation-query-routes.test.ts +1 -108
  258. package/src/runtime/routes/__tests__/mcp-add-default-risk.test.ts +12 -16
  259. package/src/runtime/routes/acp-routes.test.ts +0 -15
  260. package/src/runtime/routes/acp-routes.ts +9 -72
  261. package/src/runtime/routes/app-management-routes.ts +0 -73
  262. package/src/runtime/routes/app-routes.ts +1 -1
  263. package/src/runtime/routes/conversation-list-routes.ts +3 -14
  264. package/src/runtime/routes/conversation-query-routes.ts +0 -40
  265. package/src/runtime/routes/credential-routes.ts +10 -19
  266. package/src/runtime/routes/diagnostics-routes.ts +3 -55
  267. package/src/runtime/routes/index.ts +0 -4
  268. package/src/runtime/routes/log-export-routes.ts +0 -2
  269. package/src/runtime/routes/mcp-auth-routes.ts +47 -39
  270. package/src/runtime/routes/migration-routes.ts +21 -8
  271. package/src/runtime/routes/platform-routes.ts +15 -18
  272. package/src/runtime/services/__tests__/conversation-serializer.test.ts +0 -28
  273. package/src/runtime/services/conversation-serializer.ts +3 -16
  274. package/src/runtime/sync/resource-sync-events.ts +1 -2
  275. package/src/schedule/worker.ts +1 -1
  276. package/src/security/ces-rpc-record-backend.ts +0 -7
  277. package/src/subagent/consult-context.ts +25 -12
  278. package/src/tools/acp/list-agents.test.ts +1 -3
  279. package/src/tools/acp/spawn.test.ts +11 -146
  280. package/src/tools/acp/spawn.ts +3 -21
  281. package/src/tools/acp/status.ts +3 -40
  282. package/src/tools/app-control/skill-proxy-bridge.ts +1 -2
  283. package/src/tools/capability-offer.test.ts +2 -22
  284. package/src/tools/capability-offer.ts +1 -16
  285. package/src/tools/computer-use/definitions.ts +2 -4
  286. package/src/tools/computer-use/skill-proxy-bridge.ts +1 -2
  287. package/src/tools/credentials/metadata-store.ts +0 -100
  288. package/src/tools/host-filesystem/edit.test.ts +1 -2
  289. package/src/tools/host-filesystem/edit.ts +2 -2
  290. package/src/tools/host-filesystem/read.test.ts +1 -2
  291. package/src/tools/host-filesystem/read.ts +2 -2
  292. package/src/tools/host-filesystem/transfer.test.ts +1 -2
  293. package/src/tools/host-filesystem/transfer.ts +2 -2
  294. package/src/tools/host-filesystem/write.test.ts +1 -2
  295. package/src/tools/host-filesystem/write.ts +2 -2
  296. package/src/tools/host-terminal/host-shell.test.ts +0 -16
  297. package/src/tools/host-terminal/host-shell.ts +20 -4
  298. package/src/tools/policy-context.ts +7 -6
  299. package/src/tools/subagent/spawn.ts +8 -5
  300. package/src/tools/watch/watch-retro-report.ts +8 -0
  301. package/src/util/__tests__/language-subtag.test.ts +1 -23
  302. package/src/util/fs-watcher-error.ts +36 -0
  303. package/src/util/language-subtag.ts +0 -16
  304. package/src/util/platform.ts +0 -8
  305. package/src/workspace/git-service.ts +54 -5
  306. package/src/workspace/migrations/registry.ts +0 -6
  307. package/scripts/smoke-desktop-window-theme.ts +0 -186
  308. package/src/__tests__/git-porcelain.test.ts +0 -47
  309. package/src/__tests__/helpers/set-workspace-mcp.ts +0 -11
  310. package/src/__tests__/message-deleted-hook-dispatch.test.ts +0 -119
  311. package/src/__tests__/resolve-app.test.ts +0 -135
  312. package/src/__tests__/source-fingerprint.test.ts +0 -184
  313. package/src/__tests__/workspace-migration-154-repair-retired-codex-gpt-5-4-model-ids.test.ts +0 -336
  314. package/src/acp/__tests__/helpers/acp-model-option.ts +0 -51
  315. package/src/acp/model-config.test.ts +0 -166
  316. package/src/acp/model-config.ts +0 -138
  317. package/src/api/events/acp-session-model-update.test.ts +0 -88
  318. package/src/api/events/acp-session-model-update.ts +0 -46
  319. package/src/apps/resolve-app.ts +0 -81
  320. package/src/apps/source-fingerprint.ts +0 -266
  321. package/src/calls/__tests__/barge-in-guard.test.ts +0 -81
  322. package/src/calls/__tests__/voice-leg-coordinator.test.ts +0 -229
  323. package/src/calls/__tests__/voice-progress-cadence.test.ts +0 -274
  324. package/src/calls/barge-in-guard.ts +0 -118
  325. package/src/calls/voice-leg-coordinator.ts +0 -189
  326. package/src/calls/voice-progress-cadence.ts +0 -423
  327. package/src/cli/commands/__tests__/apps.test.ts +0 -245
  328. package/src/cli/commands/__tests__/roadmap.help.test.ts +0 -19
  329. package/src/cli/commands/channels/__tests__/send.test.ts +0 -218
  330. package/src/cli/commands/channels/send.ts +0 -128
  331. package/src/config/__tests__/platform-identity.test.ts +0 -117
  332. package/src/config/acp-agent-write.ts +0 -43
  333. package/src/config/acp-schema.test.ts +0 -81
  334. package/src/config/platform-identity.ts +0 -144
  335. package/src/config/schemas/__tests__/voice.test.ts +0 -148
  336. package/src/config/schemas/voice.ts +0 -150
  337. package/src/daemon/__tests__/skill-memory-refresh-mtime.test.ts +0 -133
  338. package/src/daemon/app-change-notify.ts +0 -45
  339. package/src/desktop/__tests__/fake-desktop.ts +0 -119
  340. package/src/desktop/desktop-chrome-policy.test.ts +0 -71
  341. package/src/desktop/desktop-chrome-policy.ts +0 -42
  342. package/src/desktop/desktop-dependencies.test.ts +0 -102
  343. package/src/desktop/desktop-dependencies.ts +0 -306
  344. package/src/desktop/desktop-feature.test.ts +0 -18
  345. package/src/desktop/desktop-feature.ts +0 -19
  346. package/src/desktop/desktop-panel-config.test.ts +0 -135
  347. package/src/desktop/desktop-panel-config.ts +0 -149
  348. package/src/desktop/desktop-session-manager.test.ts +0 -627
  349. package/src/desktop/desktop-session-manager.ts +0 -814
  350. package/src/desktop/desktop-stream-bridge.test.ts +0 -395
  351. package/src/desktop/desktop-stream-bridge.ts +0 -214
  352. package/src/desktop/desktop-wallpaper.test.ts +0 -191
  353. package/src/desktop/desktop-wallpaper.ts +0 -113
  354. package/src/desktop/desktop-window-theme.ts +0 -170
  355. package/src/i18n/AGENTS.md +0 -22
  356. package/src/i18n/__tests__/i18n.test.ts +0 -108
  357. package/src/i18n/index.ts +0 -16
  358. package/src/i18n/locales.ts +0 -93
  359. package/src/i18n/messages.ts +0 -61
  360. package/src/i18n/title.ts +0 -25
  361. package/src/mcp/__tests__/workspace-mcp-config.test.ts +0 -135
  362. package/src/mcp/spec-schema.ts +0 -111
  363. package/src/mcp/workspace-mcp-config.ts +0 -188
  364. package/src/messaging/providers/__tests__/proactive-address.test.ts +0 -95
  365. package/src/persistence/conversation-title-placeholders.ts +0 -23
  366. package/src/persistence/message-cursor.ts +0 -78
  367. package/src/persistence/migrations/__tests__/157-invite-contact-id.test.ts +0 -149
  368. package/src/plugins/defaults/memory/__tests__/memory-retrospective-cursor-backfill.test.ts +0 -118
  369. package/src/plugins/defaults/memory/__tests__/memory-retrospective-cursor-preserve.test.ts +0 -83
  370. package/src/plugins/defaults/memory/hooks/message-deleted.ts +0 -21
  371. package/src/plugins/defaults/memory/memory-retrospective-cursor-backfill.ts +0 -126
  372. package/src/plugins/defaults/memory/memory-retrospective-cursor-preserve.ts +0 -79
  373. package/src/plugins/defaults/memory/memory-retrospective-cursor.ts +0 -28
  374. package/src/plugins/defaults/memory/skill-md-mtime-poll.ts +0 -9
  375. package/src/providers/gemini-thought-signature.test.ts +0 -63
  376. package/src/providers/gemini-thought-signature.ts +0 -44
  377. package/src/providers/openai/__tests__/chat-completions-provider-thought-signature.test.ts +0 -613
  378. package/src/providers/openai/__tests__/google-thought-signature.test.ts +0 -235
  379. package/src/providers/openai/google-thought-signature.ts +0 -320
  380. package/src/runtime/__tests__/channel-send.test.ts +0 -443
  381. package/src/runtime/__tests__/desktop-stream-upgrade.test.ts +0 -89
  382. package/src/runtime/__tests__/live-voice-upgrade.test.ts +0 -58
  383. package/src/runtime/__tests__/runtime-ws-test-utils.ts +0 -72
  384. package/src/runtime/__tests__/watch-stream-upgrade.test.ts +0 -59
  385. package/src/runtime/channel-send.ts +0 -316
  386. package/src/runtime/routes/__tests__/apps-refresh-route.test.ts +0 -205
  387. package/src/runtime/routes/__tests__/channel-send-routes.test.ts +0 -127
  388. package/src/runtime/routes/__tests__/dictation-cleanup-guard.test.ts +0 -107
  389. package/src/runtime/routes/channel-send-routes.ts +0 -85
  390. package/src/runtime/routes/desktop-setup-routes.test.ts +0 -74
  391. package/src/runtime/routes/desktop-setup-routes.ts +0 -35
  392. package/src/security/__tests__/ces-http-record-backend.test.ts +0 -137
  393. package/src/security/ces-http-record-backend.ts +0 -120
  394. package/src/skills/__tests__/workspace-skill-md-signature.test.ts +0 -60
  395. package/src/skills/workspace-skill-md-signature.ts +0 -50
  396. package/src/tools/acp/status.test.ts +0 -94
  397. package/src/util/ca-bundle.ts +0 -13
  398. package/src/workspace/git-porcelain.ts +0 -66
  399. package/src/workspace/migrations/154-repair-retired-codex-gpt-5-4-model-ids.ts +0 -258
  400. package/src/workspace/migrations/155-move-front-model-config-to-voice.ts +0 -78
  401. package/src/workspace/migrations/156-extract-workspace-mcp-json.ts +0 -214
  402. package/src/workspace/migrations/__tests__/155-move-front-model-config-to-voice.test.ts +0 -102
  403. package/src/workspace/migrations/__tests__/156-extract-workspace-mcp-json.test.ts +0 -199
  404. /package/src/{calls → live-voice}/progress-phrases.ts +0 -0
package/src/acp/types.ts CHANGED
@@ -4,20 +4,14 @@
4
4
 
5
5
  import type { StopReason } from "@agentclientprotocol/sdk";
6
6
 
7
- import type { AcpAgentConfig as ConfiguredAcpAgent } from "../config/acp-schema.js";
8
- import type { AcpModelOption } from "./model-config.js";
9
-
10
7
  /**
11
- * A configured ACP agent plus what the daemon learns about it at spawn time.
12
- * The configured half is the schema's own inferred type, so a new config leaf
13
- * is declared once, in `config/acp-schema.ts`.
8
+ * Configuration for a single ACP agent process.
14
9
  */
15
- export interface AcpAgentConfig extends ConfiguredAcpAgent {
16
- /**
17
- * Always set on a resolved agent: the resolver fills in a bundled profile's
18
- * command when the config entry omits it.
19
- */
10
+ export interface AcpAgentConfig {
20
11
  command: string;
12
+ args: string[];
13
+ description?: string;
14
+ env?: Record<string, string>;
21
15
  /**
22
16
  * Identity of the Claude token `prepareAgentEnv` resolved into `env`,
23
17
  * whichever source it came from. Recorded on the history row when Claude
@@ -57,32 +51,6 @@ export interface AcpSessionState {
57
51
  authErrorCredential?: string;
58
52
  /** Latest context-window usage gauge, from the most recent `usage_update`. */
59
53
  latestUsage?: AcpUsageSnapshot;
60
- /**
61
- * Model the session is running on, as the adapter reports it. Absent while
62
- * the adapter advertises no model selector, which is how the feature stays
63
- * invisible for agents that cannot switch models.
64
- */
65
- model?: string;
66
- /** Models the adapter offers this session, flattened from its selector. */
67
- availableModels?: AcpModelOption[];
68
- /** Time-ordered identifier of the assistant process issuing revisions. */
69
- modelRevisionEpoch?: string;
70
- /** Monotonic revision within `modelRevisionEpoch`. */
71
- modelRevision?: number;
72
- }
73
-
74
- /**
75
- * Statuses a session is still live in. One list for every place that asks the
76
- * question: the boot sweep over persisted rows, the in-memory liveness guard,
77
- * `close()`, and the delete route's conflict guard.
78
- */
79
- export const ACP_LIVE_STATUSES = ["running", "initializing"] as const;
80
-
81
- /** Whether a status is one a session can still move from. */
82
- export function isLiveAcpStatus(
83
- status: AcpSessionState["status"],
84
- ): status is (typeof ACP_LIVE_STATUSES)[number] {
85
- return ACP_LIVE_STATUSES.some((live) => live === status);
86
54
  }
87
55
 
88
56
  /** Context-window usage snapshot tracked from ACP `usage_update`. */
@@ -96,16 +64,3 @@ export interface AcpUsageSnapshot {
96
64
  /** Cumulative output tokens across all turns, from `PromptResponse.usage`. */
97
65
  outputTokens?: number;
98
66
  }
99
-
100
- /**
101
- * The adapter answered `session/set_config_option` with an error: the value
102
- * was refused. Raised only for the adapter's own answer to that request, so a
103
- * closed connection, an exited process, or a failed authentication is never
104
- * mistaken for a refusal.
105
- */
106
- export class AcpConfigOptionRefusedError extends Error {
107
- constructor(message: string) {
108
- super(message);
109
- this.name = "AcpConfigOptionRefusedError";
110
- }
111
- }
@@ -1,10 +1,9 @@
1
1
  /**
2
2
  * `app_files_changed` SSE event.
3
3
  *
4
- * Broadcast after an app is created, compiled, or otherwise updated so
5
- * connected clients re-read the app (refresh preview, reload the running
6
- * surface). Workspace compiles go through `assistant apps refresh` or
7
- * `app_refresh`; file edits do not emit this on their own.
4
+ * Broadcast when an app's source files change on disk — emitted when a new
5
+ * app is created and by the app source watcher on edits — so connected
6
+ * clients re-read the app (refresh preview, reload the running surface).
8
7
  *
9
8
  * Canonical wire-contract source. Daemon code imports the type
10
9
  * directly from this file; external consumers import via
package/src/api/index.ts CHANGED
@@ -3,7 +3,6 @@ import { z } from "zod";
3
3
  import { AcpAuthRequiredEventSchema } from "./events/acp-auth-required.js";
4
4
  import { AcpSessionCompletedEventSchema } from "./events/acp-session-completed.js";
5
5
  import { AcpSessionErrorEventSchema } from "./events/acp-session-error.js";
6
- import { AcpSessionModelUpdateEventSchema } from "./events/acp-session-model-update.js";
7
6
  import { AcpSessionSpawnedEventSchema } from "./events/acp-session-spawned.js";
8
7
  import { AcpSessionUpdateEventSchema } from "./events/acp-session-update.js";
9
8
  import { AcpSessionUsageEventSchema } from "./events/acp-session-usage.js";
@@ -187,10 +186,6 @@ export {
187
186
  type AcpSessionErrorEvent,
188
187
  AcpSessionErrorEventSchema,
189
188
  } from "./events/acp-session-error.js";
190
- export {
191
- type AcpSessionModelUpdateEvent,
192
- AcpSessionModelUpdateEventSchema,
193
- } from "./events/acp-session-model-update.js";
194
189
  export {
195
190
  type AcpSessionSpawnedEvent,
196
191
  AcpSessionSpawnedEventSchema,
@@ -969,7 +964,6 @@ export const AssistantEventSchema = z.discriminatedUnion("type", [
969
964
  AcpAuthRequiredEventSchema,
970
965
  AcpSessionCompletedEventSchema,
971
966
  AcpSessionErrorEventSchema,
972
- AcpSessionModelUpdateEventSchema,
973
967
  AcpSessionSpawnedEventSchema,
974
968
  AcpSessionUpdateEventSchema,
975
969
  AcpSessionUsageEventSchema,
@@ -114,7 +114,7 @@ export function resolveEffectiveAppHtmlFromDir(sourceDir: string): string {
114
114
  if (isLegacySingleFileDir(sourceDir)) {
115
115
  return UNSUPPORTED_LEGACY_APP_HTML;
116
116
  }
117
- return `<p>App compilation failed. Run <code>assistant apps refresh</code> to rebuild.</p>`;
117
+ return `<p>App compilation failed. Edit a source file to trigger a rebuild.</p>`;
118
118
  }
119
119
 
120
120
  /**
@@ -13,10 +13,6 @@ import { existsSync, rmSync } from "node:fs";
13
13
  import { mkdir, readdir, readFile, writeFile } from "node:fs/promises";
14
14
  import { delimiter, dirname, join, resolve } from "node:path";
15
15
 
16
- import {
17
- computeAppSourceFingerprint,
18
- writeAppSourceFingerprint,
19
- } from "../apps/source-fingerprint.js";
20
16
  import { getLogger } from "../util/logger.js";
21
17
  import { ensureCompilerTools } from "./compiler-tools.js";
22
18
  import {
@@ -432,8 +428,6 @@ export async function runCompile(
432
428
  };
433
429
  }
434
430
 
435
- const sourceFingerprint = computeAppSourceFingerprint(appDir);
436
-
437
431
  // Clear stale dist/ output so removed assets (e.g. CSS) don't persist
438
432
  if (existsSync(distDir)) {
439
433
  rmSync(distDir, { recursive: true, force: true });
@@ -556,15 +550,6 @@ export async function runCompile(
556
550
  await writeFile(join(distDir, "index.html"), html);
557
551
  }
558
552
 
559
- try {
560
- writeAppSourceFingerprint(appDir, distDir, sourceFingerprint);
561
- } catch (err) {
562
- log.warn(
563
- { err, appDir, distDir },
564
- "Failed to write source fingerprint after compile",
565
- );
566
- }
567
-
568
553
  const durationMs = Math.round(performance.now() - start);
569
554
  log.info({ durationMs }, "Build succeeded");
570
555
  return { ok: true, errors: [], warnings: [], durationMs };
@@ -1,7 +1,7 @@
1
1
  import { describe, expect, test } from "bun:test";
2
2
 
3
3
  import {
4
- createControlMarkerHoldback,
4
+ couldBeControlMarker,
5
5
  ESCALATE_VERDICT_TOKEN,
6
6
  HOLD_VERDICT_TOKEN,
7
7
  isIncompleteControlMarkerTail,
@@ -28,7 +28,21 @@ describe("front-door verdict tokens", () => {
28
28
  ).toBe(" one two ");
29
29
  });
30
30
 
31
+ test("couldBeControlMarker holds the complete tokens (not flushed to TTS)", () => {
32
+ expect(couldBeControlMarker("[0]")).toBe(true);
33
+ expect(couldBeControlMarker("[1]")).toBe(true);
34
+ });
35
+
36
+ test("couldBeControlMarker holds a partial token still streaming", () => {
37
+ // Any prefix of a token must be held so a streamed "[1" does not leak
38
+ // to the TTS engine before the full token arrives.
39
+ for (const partial of ["[", "[0", "[1"]) {
40
+ expect(couldBeControlMarker(partial)).toBe(true);
41
+ }
42
+ });
43
+
31
44
  test("ordinary text is not mistaken for a token", () => {
45
+ expect(couldBeControlMarker("Sure, one moment")).toBe(false);
32
46
  expect(stripInternalSpeechMarkers("Sure, one moment")).toBe(
33
47
  "Sure, one moment",
34
48
  );
@@ -45,6 +59,16 @@ describe("minimize-room marker", () => {
45
59
  stripInternalSpeechMarkers("Done [-1] here").replace(/\s+/g, " "),
46
60
  ).toBe("Done here");
47
61
  });
62
+
63
+ test("couldBeControlMarker holds the marker and its streaming prefixes", () => {
64
+ for (const text of ["[", "[-", "[-1", "[-1]", "[-1] trailing"]) {
65
+ expect(couldBeControlMarker(text)).toBe(true);
66
+ }
67
+ });
68
+
69
+ test("a bracket prefix that disproves the marker is not held", () => {
70
+ expect(couldBeControlMarker("[- something else")).toBe(false);
71
+ });
48
72
  });
49
73
 
50
74
  describe("isIncompleteControlMarkerTail", () => {
@@ -79,60 +103,3 @@ describe("isIncompleteControlMarkerTail", () => {
79
103
  }
80
104
  });
81
105
  });
82
-
83
- describe("createControlMarkerHoldback", () => {
84
- function collect(): {
85
- flush: ReturnType<typeof createControlMarkerHoldback>;
86
- chunks: string[];
87
- } {
88
- const chunks: string[] = [];
89
- const flush = createControlMarkerHoldback((chunk) => chunks.push(chunk));
90
- return { flush, chunks };
91
- }
92
-
93
- test("holds a token still streaming and strips it once complete", () => {
94
- const { flush, chunks } = collect();
95
- flush("Sure [");
96
- expect(chunks).toEqual(["Sure "]);
97
- flush("Sure [1");
98
- expect(chunks).toEqual(["Sure "]);
99
- flush("Sure [1] one moment");
100
- expect(chunks).toEqual(["Sure ", " one moment"]);
101
- });
102
-
103
- test("ordinary bracketed text flushes without stalling", () => {
104
- const { flush, chunks } = collect();
105
- flush("Option [A] then [note] here");
106
- expect(chunks).toEqual(["Option [A] then [note] here"]);
107
- });
108
-
109
- test("a bracket prefix that disproves every marker flushes", () => {
110
- const { flush, chunks } = collect();
111
- flush("[- something else");
112
- expect(chunks).toEqual(["[- something else"]);
113
- });
114
-
115
- test("a guardian-approval body is held until its JSON balances", () => {
116
- const { flush, chunks } = collect();
117
- const streaming =
118
- 'Hold on. [ASK_GUARDIAN_APPROVAL: {"question": "ok]?", "options": ["a", "b"';
119
- flush(streaming);
120
- expect(chunks).toEqual(["Hold on. "]);
121
- flush(`${streaming}]}] Thanks.`);
122
- expect(chunks).toEqual(["Hold on. ", " Thanks."]);
123
- });
124
-
125
- test("force emits a held tail that never became a marker", () => {
126
- const { flush, chunks } = collect();
127
- flush("Score was [1");
128
- expect(chunks).toEqual(["Score was "]);
129
- flush("Score was [1", { force: true });
130
- expect(chunks).toEqual(["Score was ", "[1"]);
131
- });
132
-
133
- test("a chunk that strips to nothing is not emitted", () => {
134
- const { flush, chunks } = collect();
135
- flush("[END_CALL]");
136
- expect(chunks).toEqual([]);
137
- });
138
- });
@@ -842,42 +842,6 @@ describe("startVoiceTurn triage-and-escalate control prompt", () => {
842
842
  expect(installed()).toContain(escalatedContinuationRule());
843
843
  });
844
844
 
845
- test("the auto-built phone prompt carries the front-door rule anchored to the caller's words", async () => {
846
- const installed = captureInstalledPrompt();
847
- await startVoiceTurn({
848
- ...makeTurnOptions(),
849
- content: "what time is it",
850
- routingLeg: "front-door",
851
- });
852
- expect(installed()).toContain("<voice_call_control>");
853
- expect(installed()).toContain(
854
- `13. ${frontDoorDecisionRule({ callerUtterance: "what time is it" })}`,
855
- );
856
- });
857
-
858
- test("a phone sentinel anchors the front-door rule on its persisted form", async () => {
859
- const installed = captureInstalledPrompt();
860
- await startVoiceTurn({ ...makeTurnOptions(), routingLeg: "front-door" });
861
- expect(installed()).toContain(
862
- frontDoorDecisionRule({
863
- callerUtterance: "(call connected — deliver opening greeting)",
864
- }),
865
- );
866
- expect(installed()).not.toContain(JSON.stringify(CALL_OPENING_MARKER));
867
- });
868
-
869
- test("the auto-built phone prompt carries the escalated continuation rule", async () => {
870
- const installed = captureInstalledPrompt();
871
- await startVoiceTurn({
872
- ...makeTurnOptions(),
873
- routingLeg: "escalated",
874
- spokenEscalationBridge: "One moment.",
875
- });
876
- expect(installed()).toContain(
877
- `13. ${escalatedContinuationRule("One moment.")}`,
878
- );
879
- });
880
-
881
845
  test("leaves a caller-supplied prompt verbatim when no routing leg is set", async () => {
882
846
  const installed = captureInstalledPrompt();
883
847
  await startVoiceTurn({
@@ -896,7 +860,7 @@ describe("default call protocol numbered rules", () => {
896
860
  const installed = captureInstalledPrompt();
897
861
  await startVoiceTurn(makeTurnOptions());
898
862
  expect(installed()).toContain(
899
- "11. Speak the caller's language: reply in the language of the caller's most recent actual speech, and follow them if they switch languages mid-call. Synthetic user turns (parenthetical markers like the call-connected and verification-completed notices) are not caller speech and never set the language. Before the caller has spoken, such as on the opening greeting turn, use the language the Task context implies, if any; otherwise default to English.",
863
+ "12. Speak the caller's language: reply in the language of the caller's most recent actual speech, and follow them if they switch languages mid-call. Synthetic user turns (parenthetical markers like the call-connected and verification-completed notices) are not caller speech and never set the language. Before the caller has spoken, such as on the opening greeting turn, use the language the Task context implies, if any; otherwise default to English.",
900
864
  );
901
865
  });
902
866
 
@@ -5,7 +5,6 @@ import {
5
5
  capEscalationBridge,
6
6
  classifyFrontDoorLeading,
7
7
  createFrontDoorStreamGate,
8
- createFrontDoorVerdictMachine,
9
8
  ESCALATE_VERDICT_TOKEN,
10
9
  escalatedContinuationRule,
11
10
  ESCALATION_CONTINUATION_CONTENT,
@@ -18,7 +17,6 @@ import {
18
17
  isEscalationBridgeComplete,
19
18
  MAX_ESCALATION_BRIDGE_CHARS,
20
19
  needsFallbackBridge,
21
- resolveSpokenEscalationBridge,
22
20
  spokenBridgeText,
23
21
  } from "../voice-triage-escalate.js";
24
22
 
@@ -283,34 +281,6 @@ describe("fallbackEscalationBridgeFor", () => {
283
281
  });
284
282
  });
285
283
 
286
- describe("resolveSpokenEscalationBridge", () => {
287
- test("a real capped bridge is spoken as the model's own speech", () => {
288
- expect(resolveSpokenEscalationBridge("Let me check that.", "es")).toEqual({
289
- spokenBridge: "Let me check that.",
290
- usesFallback: false,
291
- });
292
- });
293
-
294
- test("an empty or too-short bridge falls back to the localized canned phrase, audio-only", () => {
295
- expect(resolveSpokenEscalationBridge("", "es")).toEqual({
296
- spokenBridge: FALLBACK_ESCALATION_BRIDGE_BY_LANGUAGE.es,
297
- usesFallback: true,
298
- });
299
- expect(resolveSpokenEscalationBridge("Ok", undefined)).toEqual({
300
- spokenBridge: FALLBACK_ESCALATION_BRIDGE,
301
- usesFallback: true,
302
- });
303
- });
304
-
305
- test("a canned phrase the table lacks for the caller's language is English and says so", () => {
306
- expect(resolveSpokenEscalationBridge("", "ko")).toEqual({
307
- spokenBridge: FALLBACK_ESCALATION_BRIDGE,
308
- usesFallback: true,
309
- language: "en",
310
- });
311
- });
312
- });
313
-
314
284
  describe("capEscalationBridge", () => {
315
285
  test("cuts just after the first sentence terminator", () => {
316
286
  expect(
@@ -479,81 +449,6 @@ describe("live-voice escalation orchestration (end-to-end — TODO)", () => {
479
449
  );
480
450
  });
481
451
 
482
- describe("createFrontDoorVerdictMachine", () => {
483
- /** Feed `deltas` through a machine and return the step kinds, in order. */
484
- function kinds(deltas: string[], holdEnabled = false): string[] {
485
- const machine = createFrontDoorVerdictMachine(holdEnabled);
486
- return deltas.map((delta) => machine.push(delta).kind);
487
- }
488
-
489
- test("stays pending while the lead could still become a token", () => {
490
- expect(kinds(["", "[", "1"])).toEqual(["pending", "pending", "pending"]);
491
- });
492
-
493
- test("an answer releases the held lead on the transition, then each delta", () => {
494
- const machine = createFrontDoorVerdictMachine(false);
495
- expect(machine.push("[")).toEqual({ kind: "pending" });
496
- expect(machine.push("A] first")).toEqual({
497
- kind: "answer",
498
- text: "[A] first",
499
- });
500
- expect(machine.push(", second")).toEqual({
501
- kind: "answer",
502
- text: ", second",
503
- });
504
- });
505
-
506
- test("escalate reports the capped bridge on the delta that completes it", () => {
507
- const machine = createFrontDoorVerdictMachine(false);
508
- expect(machine.push(`${ESCALATE_VERDICT_TOKEN} One `)).toEqual({
509
- kind: "escalate",
510
- bridge: null,
511
- });
512
- expect(machine.push("moment")).toEqual({ kind: "bridging" });
513
- expect(machine.push(". Extra text past the cap")).toEqual({
514
- kind: "bridge",
515
- bridge: "One moment.",
516
- });
517
- expect(machine.push(" more")).toEqual({ kind: "done" });
518
- });
519
-
520
- test("a bridge that completes on the verdict delta is reported with it", () => {
521
- const machine = createFrontDoorVerdictMachine(false);
522
- expect(machine.push(`${ESCALATE_VERDICT_TOKEN} Let me check.`)).toEqual({
523
- kind: "escalate",
524
- bridge: "Let me check.",
525
- });
526
- });
527
-
528
- test("finish hands off a bridge that never hit a terminator", () => {
529
- const machine = createFrontDoorVerdictMachine(false);
530
- machine.push(`${ESCALATE_VERDICT_TOKEN} Give me a second`);
531
- expect(machine.finish()).toEqual({
532
- kind: "bridge",
533
- bridge: "Give me a second",
534
- });
535
- expect(machine.push("late")).toEqual({ kind: "done" });
536
- });
537
-
538
- test("finish on an answer or a pending lead is done, not a bridge", () => {
539
- const answering = createFrontDoorVerdictMachine(false);
540
- answering.push("Sure.");
541
- expect(answering.finish()).toEqual({ kind: "done" });
542
- const undecided = createFrontDoorVerdictMachine(false);
543
- undecided.push("[");
544
- expect(undecided.finish()).toEqual({ kind: "done" });
545
- });
546
-
547
- test("hold is a step only when the leg was taught the token", () => {
548
- expect(kinds([HOLD_VERDICT_TOKEN], true)).toEqual(["hold"]);
549
- expect(kinds([`${HOLD_VERDICT_TOKEN} trailing`], true)).toEqual(["hold"]);
550
- expect(kinds([HOLD_VERDICT_TOKEN], false)).toEqual(["answer"]);
551
- const held = createFrontDoorVerdictMachine(true);
552
- held.push(HOLD_VERDICT_TOKEN);
553
- expect(held.push("anything")).toEqual({ kind: "done" });
554
- });
555
- });
556
-
557
452
  describe("createFrontDoorStreamGate", () => {
558
453
  /** Feed `deltas` through a gate and return what it released, in order. */
559
454
  function release(
@@ -69,35 +69,15 @@ export function getGuardianWaitUpdateSteadyMaxIntervalMs(): number {
69
69
  return getConfig().calls.guardianWaitUpdateSteadyMaxIntervalMs;
70
70
  }
71
71
 
72
- // Fixed conversational timings. Named here, beside the config-backed limits
73
- // above, so the phone path's cadence is readable in one place.
74
-
75
- /** Caller silence after the assistant's turn before it nudges them. */
76
- export const CALLER_SILENCE_NUDGE_MS = 30_000;
77
-
78
- /** Listen window after the goodbye drains, in case the caller re-engages. */
79
- export const END_CALL_LISTEN_WINDOW_MS = 2_000;
80
-
81
- /** Max time to wait for goodbye audio to drain before forcing hangup. */
82
- export const END_CALL_DRAIN_MAX_WAIT_MS = 15_000;
83
-
84
- /** Lead before the max call duration at which the low-on-time warning is spoken. */
85
- export const DURATION_WARNING_LEAD_MS = 2 * 60 * 1000;
86
-
87
- /** Delay after the max-duration goodbye is spoken before the call is ended. */
88
- export const POST_GOODBYE_HANGUP_DELAY_MS = 3_000;
89
-
90
- /** Cap on waiting for a superseded turn's teardown before the next caller turn starts. */
91
- export const BARGE_IN_TEARDOWN_WAIT_MS = 2_000;
92
-
93
72
  export function getSilenceTimeoutMs(): number {
94
- return CALLER_SILENCE_NUDGE_MS;
73
+ return 30 * 1000; // 30 seconds
95
74
  }
96
75
 
97
76
  export function getEndCallListenWindowMs(): number {
98
- return END_CALL_LISTEN_WINDOW_MS;
77
+ return 2 * 1000;
99
78
  }
100
79
 
80
+ /** Max time to wait for goodbye audio to drain before forcing hangup. */
101
81
  export function getEndCallDrainMaxWaitMs(): number {
102
- return END_CALL_DRAIN_MAX_WAIT_MS;
82
+ return 15 * 1000;
103
83
  }