@xopcai/xopc 0.0.241 → 0.0.243

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 (257) hide show
  1. package/dist/browser-ext/manifest.json +1 -1
  2. package/dist/extensions/telegram/xopc.extension.json +1 -1
  3. package/dist/gateway/static/root/assets/{activity-store-CLnbVm9G.js → activity-store-CAah-_8h.js} +1 -1
  4. package/dist/gateway/static/root/assets/{agent-avatar-dicebear-DuBewmbW.js → agent-avatar-dicebear-DDH4HgP7.js} +1 -1
  5. package/dist/gateway/static/root/assets/agent-defaults-settings-panel-BDCfJZhh.js +1 -0
  6. package/dist/gateway/static/root/assets/agents-B0ZWgf-U.js +1 -0
  7. package/dist/gateway/static/root/assets/{api-DjBZe303.js → api-B2tKxbcz.js} +1 -1
  8. package/dist/gateway/static/root/assets/app-management-settings-panel-Blfwszzn.js +1 -0
  9. package/dist/gateway/static/root/assets/{appearance-settings-B-iul0RG.js → appearance-settings-C3V7Na75.js} +1 -1
  10. package/dist/gateway/static/root/assets/apps-page-BiEks0-F.js +1 -0
  11. package/dist/gateway/static/root/assets/{archive-plugin-BOx0EJZs.js → archive-plugin-BmSx7wzY.js} +1 -1
  12. package/dist/gateway/static/root/assets/{attachment-load-Cfk1lwBo.js → attachment-load-BS-S4LJ9.js} +1 -1
  13. package/dist/gateway/static/root/assets/{automations-page-BTSGvaeS.js → automations-page-C7Y3L30D.js} +1 -1
  14. package/dist/gateway/static/root/assets/automations-workspace-A3zPkPuo.js +6 -0
  15. package/dist/gateway/static/root/assets/{binary-plugins-ChZyZK45.js → binary-plugins-BM9B5kcm.js} +1 -1
  16. package/dist/gateway/static/root/assets/block-editor-BbnpkYP9.js +185 -0
  17. package/dist/gateway/static/root/assets/browser-settings-page-Dk4FQ7fY.js +8 -0
  18. package/dist/gateway/static/root/assets/{browser-workflow-inputs-jvfcgFG-.js → browser-workflow-inputs-CRnkgZHI.js} +1 -1
  19. package/dist/gateway/static/root/assets/{browser-workflows-page-DrHW7XNi.js → browser-workflows-page-B9qGL-it.js} +2 -2
  20. package/dist/gateway/static/root/assets/{button-CSEbl4zT.js → button-CtTvuElV.js} +1 -1
  21. package/dist/gateway/static/root/assets/capabilities-settings-panel--tR_El9e.js +7 -0
  22. package/dist/gateway/static/root/assets/channels-settings-D347vl_J.js +1 -0
  23. package/dist/gateway/static/root/assets/{channels-status-swr-CC9MFway.js → channels-status-swr-DuY4MGxe.js} +1 -1
  24. package/dist/gateway/static/root/assets/{chat-terminal-dock-DeeZrVbV.js → chat-terminal-dock-DABPvwBT.js} +2 -2
  25. package/dist/gateway/static/root/assets/connectors-page-B-tvJkRJ.js +2 -0
  26. package/dist/gateway/static/root/assets/{cron-expression-CiqQOeQ3.js → cron-expression-D3bsKbNd.js} +1 -1
  27. package/dist/gateway/static/root/assets/{date-picker-CGAMGPfU.js → date-picker-BsGM6Yty.js} +1 -1
  28. package/dist/gateway/static/root/assets/{dependency-picker-CxWeUTsc.js → dependency-picker-Dj3g6YXZ.js} +1 -1
  29. package/dist/gateway/static/root/assets/{desktop-pet-C3QmYO75.js → desktop-pet-C1QT0Sur.js} +1 -1
  30. package/dist/gateway/static/root/assets/{desktop-pet-settings-CAADkWYy.js → desktop-pet-settings-r6kAOnfY.js} +1 -1
  31. package/dist/gateway/static/root/assets/dist-CpzYSoz7.js +1 -0
  32. package/dist/gateway/static/root/assets/{dist-DaxPZj9e.js → dist-DBS3OB8K.js} +1 -1
  33. package/dist/gateway/static/root/assets/dist-DLmwHyAh.js +1 -0
  34. package/dist/gateway/static/root/assets/es2015-BvLh9GaE.js +41 -0
  35. package/dist/gateway/static/root/assets/{extension-debug-page-FQXjDJ8P.js → extension-debug-page-DOkf7nh9.js} +1 -1
  36. package/dist/gateway/static/root/assets/{extension-page-BJE1D5Ji.js → extension-page-Cq2IA4Ho.js} +1 -1
  37. package/dist/gateway/static/root/assets/{extension-settings-page-5Ik2tNry.js → extension-settings-page-DQn4qjDZ.js} +1 -1
  38. package/dist/gateway/static/root/assets/{files-DQjhZjr2.js → files-D6vf3S30.js} +1 -1
  39. package/dist/gateway/static/root/assets/{gateway-config-api-cTj71t2a.js → gateway-config-api-DM3poL22.js} +1 -1
  40. package/dist/gateway/static/root/assets/{gateway-config-swr-Bxe_R-JH.js → gateway-config-swr-BC3pgb_P.js} +1 -1
  41. package/dist/gateway/static/root/assets/{gateway-settings-KXBUjNcx.js → gateway-settings-DPgH1hnh.js} +1 -1
  42. package/dist/gateway/static/root/assets/{gateway-startup-retry-DJG-I0wW.js → gateway-startup-retry-uMcSfLru.js} +1 -1
  43. package/dist/gateway/static/root/assets/{heartbeat-settings-C8cVzIcs.js → heartbeat-settings-Bk80-E3b.js} +1 -1
  44. package/dist/gateway/static/root/assets/home-page-DKo5JiMR.js +1 -0
  45. package/dist/gateway/static/root/assets/{image-generation-api-Dc_ojQuj.js → image-generation-api-D1qlQA-A.js} +1 -1
  46. package/dist/gateway/static/root/assets/index-B0WJL9N1.js +71 -0
  47. package/dist/gateway/static/root/assets/index-Dbh5SXyV.css +2 -0
  48. package/dist/gateway/static/root/assets/{keyboard-shortcuts-settings-pOKl7blR.js → keyboard-shortcuts-settings-BEwvd8ZU.js} +1 -1
  49. package/dist/gateway/static/root/assets/local-app-workbench-page--eJ5rmNj.js +2 -0
  50. package/dist/gateway/static/root/assets/{local-apps-page-Bi6wwKgm.js → local-apps-page-CgkY9E-r.js} +1 -1
  51. package/dist/gateway/static/root/assets/{locale-store-C5wr3_pc.js → locale-store-CMZljTJx.js} +1 -1
  52. package/dist/gateway/static/root/assets/logs-page-Z49Td0J9.js +2 -0
  53. package/dist/gateway/static/root/assets/{management-settings-DGlVizWi.js → management-settings-Dv8NSJKt.js} +1 -1
  54. package/dist/gateway/static/root/assets/{markdown-split-CXP5zBx_.js → markdown-split-Cm0RBB-t.js} +1 -1
  55. package/dist/gateway/static/root/assets/{markdown-view-D6LxlDxr.js → markdown-view-PPCLt7fu.js} +3 -3
  56. package/dist/gateway/static/root/assets/{media-plugins-BsENGLr2.js → media-plugins-Bcr5sU1f.js} +1 -1
  57. package/dist/gateway/static/root/assets/messages-CTSgFlE4.js +3 -0
  58. package/dist/gateway/static/root/assets/mobile-pairing-wizard-kKDiXofY.js +1 -0
  59. package/dist/gateway/static/root/assets/{models-hub-cache-Y7GUjxHx.js → models-hub-cache-ZrbGRiGY.js} +1 -1
  60. package/dist/gateway/static/root/assets/{notes-page-D2EqpDyo.js → notes-page-CgsaRaGi.js} +1 -1
  61. package/dist/gateway/static/root/assets/notes-workbench-C1DEE09k.js +4 -0
  62. package/dist/gateway/static/root/assets/{oauth-api-C5NVcsKE.js → oauth-api-4VeMbkTJ.js} +1 -1
  63. package/dist/gateway/static/root/assets/popover-select-C-Hj-nXR.js +1 -0
  64. package/dist/gateway/static/root/assets/{product-delivery-dUJgmBQZ.js → product-delivery-CV4pDOtG.js} +1 -1
  65. package/dist/gateway/static/root/assets/product-open-page-BU0HiZtv.js +1 -0
  66. package/dist/gateway/static/root/assets/project-detail-page-isRapnp5.js +1 -0
  67. package/dist/gateway/static/root/assets/projects-page-zvsjg0mi.js +1 -0
  68. package/dist/gateway/static/root/assets/{registry-api-FXdFaoWM.js → registry-api-CWOtPFrE.js} +1 -1
  69. package/dist/gateway/static/root/assets/remote-access-hub-C9TGZ9Hc.js +1 -0
  70. package/dist/gateway/static/root/assets/runtime-tools-settings-panel-2zm9edMA.js +5 -0
  71. package/dist/gateway/static/root/assets/{schema-form-BUzdHWx6.js → schema-form-54A5gzkN.js} +1 -1
  72. package/dist/gateway/static/root/assets/{schemas-zIBW3wiV.js → schemas-BHS7bo06.js} +1 -1
  73. package/dist/gateway/static/root/assets/sessions-page-BP8RyiUn.js +1 -0
  74. package/dist/gateway/static/root/assets/settings-advanced-gate-D4EMxWAZ.js +1 -0
  75. package/dist/gateway/static/root/assets/{settings-page-C0OBLqpu.js → settings-page-DzDhoyxv.js} +1 -1
  76. package/dist/gateway/static/root/assets/{setup-status-panel-NpLQkFCh.js → setup-status-panel-uDicHU1w.js} +1 -1
  77. package/dist/gateway/static/root/assets/{share-preview-page-BtbPYaYC.js → share-preview-page-lOmLCWFS.js} +1 -1
  78. package/dist/gateway/static/root/assets/shares-settings-T4Yvouvv.js +1 -0
  79. package/dist/gateway/static/root/assets/skill-reload-api-DVb7nrXz.js +1 -0
  80. package/dist/gateway/static/root/assets/{skills-page-CYk8pN97.js → skills-page-CnyNH3To.js} +1 -1
  81. package/dist/gateway/static/root/assets/skills-page.utils-CgDtf2qs.js +1 -0
  82. package/dist/gateway/static/root/assets/{system-settings-panel-DmCRSvtd.js → system-settings-panel-C8yWfwtR.js} +1 -1
  83. package/dist/gateway/static/root/assets/task-detail-page-Tzfjlbf3.js +1 -0
  84. package/dist/gateway/static/root/assets/{theme-store-DUko1ZnE.js → theme-store-uxUwr10D.js} +1 -1
  85. package/dist/gateway/static/root/assets/tunnel-api-Bvg679no.js +1 -0
  86. package/dist/gateway/static/root/assets/{use-autosave-W_P8Kiv4.js → use-autosave-D88VGoyG.js} +1 -1
  87. package/dist/gateway/static/root/assets/user-context-page-RijPtyfO.js +1 -0
  88. package/dist/gateway/static/root/assets/{voice-api-key-field-BZD0j1jc.js → voice-api-key-field-CBHLsMcc.js} +1 -1
  89. package/dist/gateway/static/root/assets/voice-config-api-MqyI6cgq.js +1 -0
  90. package/dist/gateway/static/root/assets/work-discovery-overlay-GGe2TQ98.js +1 -0
  91. package/dist/gateway/static/root/assets/workflow-run-setup-panel-C0layUE9.js +3 -0
  92. package/dist/gateway/static/root/assets/workflows-page-DQXIzBAc.js +5 -0
  93. package/dist/gateway/static/root/index.html +21 -22
  94. package/dist/package.js +1 -1
  95. package/dist/packages/realtime-protocol/src/voice-audio.js +20 -0
  96. package/dist/packages/realtime-protocol/src/voice.js +208 -0
  97. package/dist/src/agent/agent-manager.js +1 -0
  98. package/dist/src/agent/embedded/run-for-session.d.ts +1 -0
  99. package/dist/src/agent/embedded/run-for-session.js +2 -1
  100. package/dist/src/agent/inbound/turn-dispatcher.d.ts +1 -0
  101. package/dist/src/agent/inbound/turn-dispatcher.js +2 -1
  102. package/dist/src/agent/prompt/voice-presentation.d.ts +2 -0
  103. package/dist/src/agent/prompt/voice-presentation.js +12 -0
  104. package/dist/src/agent/service/direct-turn-helpers.d.ts +1 -0
  105. package/dist/src/agent/service/direct-turn-helpers.js +1 -0
  106. package/dist/src/agent/service/process-direct-streaming.d.ts +1 -0
  107. package/dist/src/agent/service/process-direct-streaming.js +2 -1
  108. package/dist/src/agent/session/session-config-service.js +4 -2
  109. package/dist/src/agent/skills/installer.d.ts +1 -0
  110. package/dist/src/agent/skills/installer.js +9 -6
  111. package/dist/src/agent/tools/factory.d.ts +2 -0
  112. package/dist/src/agent/tools/factory.js +5 -1
  113. package/dist/src/automations/draft/automation-draft-service.js +1 -1
  114. package/dist/src/config/models-json.d.ts +8 -8
  115. package/dist/src/config/schema.d.ts +60 -0
  116. package/dist/src/config/schema.js +36 -4
  117. package/dist/src/extensions/install.js +1 -1
  118. package/dist/src/files/file-service.d.ts +1 -0
  119. package/dist/src/files/file-service.js +4 -0
  120. package/dist/src/gateway/chat-stream/thinking-delta-coalescer.js +8 -3
  121. package/dist/src/gateway/hono/lib/config-payload.d.ts +1 -11
  122. package/dist/src/gateway/hono/lib/config-payload.js +2 -2
  123. package/dist/src/gateway/hono/lib/safe-voice-config.d.ts +14 -0
  124. package/dist/src/gateway/hono/lib/safe-voice-config.js +29 -1
  125. package/dist/src/gateway/hono/routes/config-patch/misc.js +2 -2
  126. package/dist/src/gateway/hono/routes/files.js +7 -0
  127. package/dist/src/gateway/hono/routes/lazy-fallback.js +18 -4
  128. package/dist/src/gateway/hono/routes/runtime-tools.js +7 -1
  129. package/dist/src/gateway/hono/routes/session-input-handler.js +14 -0
  130. package/dist/src/gateway/hono/routes/sessions.js +4 -1
  131. package/dist/src/gateway/hono/routes/voice.js +140 -3
  132. package/dist/src/gateway/server.js +1 -0
  133. package/dist/src/gateway/service/agent-runner.d.ts +1 -0
  134. package/dist/src/gateway/service/agent-runner.js +1 -6
  135. package/dist/src/gateway/service/run-gateway-agent.d.ts +1 -0
  136. package/dist/src/gateway/service/run-gateway-agent.js +19 -1
  137. package/dist/src/gateway/service.d.ts +2 -0
  138. package/dist/src/gateway/service.js +73 -0
  139. package/dist/src/media-understanding/types.d.ts +61 -0
  140. package/dist/src/runtime-tools/archive.js +17 -3
  141. package/dist/src/runtime-tools/command.d.ts +1 -0
  142. package/dist/src/runtime-tools/command.js +29 -8
  143. package/dist/src/runtime-tools/environment.d.ts +1 -0
  144. package/dist/src/runtime-tools/environment.js +11 -16
  145. package/dist/src/runtime-tools/install-lock.d.ts +1 -1
  146. package/dist/src/runtime-tools/install-lock.js +34 -21
  147. package/dist/src/runtime-tools/manager.d.ts +1 -1
  148. package/dist/src/runtime-tools/manager.js +99 -64
  149. package/dist/src/runtime-tools/manifest-store.d.ts +2 -0
  150. package/dist/src/runtime-tools/manifest-store.js +29 -8
  151. package/dist/src/runtime-tools/paths.d.ts +2 -1
  152. package/dist/src/runtime-tools/paths.js +19 -8
  153. package/dist/src/runtime-tools/probe.d.ts +2 -0
  154. package/dist/src/runtime-tools/probe.js +13 -1
  155. package/dist/src/runtime-tools/prune.js +21 -7
  156. package/dist/src/session/client-history.js +12 -0
  157. package/dist/src/session/manager.d.ts +1 -0
  158. package/dist/src/session/session-context-for-llm.js +8 -0
  159. package/dist/src/session/store.d.ts +1 -0
  160. package/dist/src/session/store.js +1 -0
  161. package/dist/src/session/stored-rows-to-file-entries.js +5 -1
  162. package/dist/src/session/voice-transcript.d.ts +9 -0
  163. package/dist/src/session/voice-transcript.js +45 -0
  164. package/dist/src/storage/sqlite/config-repository.js +9 -0
  165. package/dist/src/storage/sqlite/remote-context-repository.d.ts +3 -0
  166. package/dist/src/storage/sqlite/remote-context-repository.js +40 -0
  167. package/dist/src/storage/sqlite/session-repository.js +13 -0
  168. package/dist/src/storage/sqlite/user-context-repository.d.ts +3 -1
  169. package/dist/src/storage/sqlite/user-context-repository.js +50 -4
  170. package/dist/src/tui/tui.js +2 -1
  171. package/dist/src/user-context/automatic-context.d.ts +17 -0
  172. package/dist/src/user-context/automatic-context.js +85 -0
  173. package/dist/src/user-context/changes.d.ts +7 -0
  174. package/dist/src/user-context/changes.js +28 -0
  175. package/dist/src/user-context/planner.js +1 -24
  176. package/dist/src/user-context/retriever.js +10 -11
  177. package/dist/src/user-context/selection-policy.d.ts +20 -0
  178. package/dist/src/user-context/selection-policy.js +33 -0
  179. package/dist/src/user-context/sources/index.js +2 -2
  180. package/dist/src/user-context/sources/repository.d.ts +2 -1
  181. package/dist/src/user-context/sources/repository.js +26 -5
  182. package/dist/src/voice/dashscope/streaming-stt-session.d.ts +2 -0
  183. package/dist/src/voice/dashscope/streaming-stt-session.js +249 -0
  184. package/dist/src/voice/dashscope/streaming-tts-stream.d.ts +12 -0
  185. package/dist/src/voice/dashscope/streaming-tts-stream.js +153 -0
  186. package/dist/src/voice/realtime/agentEngine.d.ts +10 -0
  187. package/dist/src/voice/realtime/agentEngine.js +403 -0
  188. package/dist/src/voice/realtime/audio-playback-window.d.ts +9 -0
  189. package/dist/src/voice/realtime/audio-playback-window.js +49 -0
  190. package/dist/src/voice/realtime/conversation-context.d.ts +11 -0
  191. package/dist/src/voice/realtime/conversation-context.js +76 -0
  192. package/dist/src/voice/realtime/engine.d.ts +13 -0
  193. package/dist/src/voice/realtime/engine.js +1 -0
  194. package/dist/src/voice/realtime/memory-context.d.ts +17 -0
  195. package/dist/src/voice/realtime/memory-context.js +100 -0
  196. package/dist/src/voice/realtime/omniEngine.d.ts +18 -0
  197. package/dist/src/voice/realtime/omniEngine.js +443 -0
  198. package/dist/src/voice/realtime/omniRoute.d.ts +10 -0
  199. package/dist/src/voice/realtime/omniRoute.js +31 -0
  200. package/dist/src/voice/realtime/runtime.d.ts +99 -0
  201. package/dist/src/voice/realtime/runtime.js +622 -0
  202. package/dist/src/voice/realtime/speakable-segmenter.d.ts +10 -0
  203. package/dist/src/voice/realtime/speakable-segmenter.js +87 -0
  204. package/dist/src/voice/stt/list-providers.js +2 -1
  205. package/dist/src/voice/stt/providers/alibaba-transcription.js +13 -1
  206. package/dist/src/voice/stt/providers/xopc-cloud-transcription.js +23 -0
  207. package/dist/src/voice/tts/factory.js +1 -0
  208. package/dist/src/voice/tts/openai-compatible-speech.js +3 -1
  209. package/dist/src/voice/tts/providers/alibaba-speech.d.ts +1 -5
  210. package/dist/src/voice/tts/providers/alibaba-speech.js +25 -8
  211. package/dist/src/voice/tts/providers/edge-speech.js +21 -22
  212. package/dist/src/voice/tts/providers/minimax-speech.js +6 -3
  213. package/dist/src/voice/tts/providers/xopc-cloud-speech.js +26 -1
  214. package/dist/src/voice/tts/speak-core.d.ts +6 -2
  215. package/dist/src/voice/tts/speak-core.js +46 -34
  216. package/dist/src/voice/tts/speech-provider-types.d.ts +1 -0
  217. package/package.json +6 -6
  218. package/dist/gateway/static/root/assets/Combination-14nmIgxH.js +0 -41
  219. package/dist/gateway/static/root/assets/agent-defaults-settings-panel-DbdgX6AA.js +0 -1
  220. package/dist/gateway/static/root/assets/agents-BX3uRVm4.js +0 -1
  221. package/dist/gateway/static/root/assets/app-chrome-BeB4KgOf.js +0 -1
  222. package/dist/gateway/static/root/assets/app-management-settings-panel-D8evZyFQ.js +0 -1
  223. package/dist/gateway/static/root/assets/apps-page-CoZd_cZu.js +0 -1
  224. package/dist/gateway/static/root/assets/automations-workspace-C8RRKT-a.js +0 -6
  225. package/dist/gateway/static/root/assets/block-editor-DCH9b2Ht.js +0 -184
  226. package/dist/gateway/static/root/assets/browser-settings-page-D1GPwIfx.js +0 -8
  227. package/dist/gateway/static/root/assets/capabilities-settings-panel-CrXB1Q-l.js +0 -7
  228. package/dist/gateway/static/root/assets/channels-settings-DWMSYaNZ.js +0 -1
  229. package/dist/gateway/static/root/assets/connectors-page-DXTl1fNB.js +0 -2
  230. package/dist/gateway/static/root/assets/dist-BPoKqzeH.js +0 -1
  231. package/dist/gateway/static/root/assets/dist-DqPZM2MH.js +0 -1
  232. package/dist/gateway/static/root/assets/home-page-NdWtBda5.js +0 -1
  233. package/dist/gateway/static/root/assets/index-7i2P3312.js +0 -70
  234. package/dist/gateway/static/root/assets/index-DTo3IcbW.css +0 -2
  235. package/dist/gateway/static/root/assets/local-app-workbench-page-C_j_od5f.js +0 -2
  236. package/dist/gateway/static/root/assets/logs-page-D6PDZEVP.js +0 -2
  237. package/dist/gateway/static/root/assets/messages-_tYhRAHD.js +0 -3
  238. package/dist/gateway/static/root/assets/mobile-pairing-wizard-DcEz7qcX.js +0 -1
  239. package/dist/gateway/static/root/assets/notes-workbench-Bu0a83Oj.js +0 -4
  240. package/dist/gateway/static/root/assets/popover-select-DrILF6mR.js +0 -1
  241. package/dist/gateway/static/root/assets/product-open-page-DMhf1rdz.js +0 -1
  242. package/dist/gateway/static/root/assets/project-detail-page-DDHi0Y4Q.js +0 -1
  243. package/dist/gateway/static/root/assets/projects-page-CVMFKpmu.js +0 -1
  244. package/dist/gateway/static/root/assets/remote-access-hub-B74aErBY.js +0 -1
  245. package/dist/gateway/static/root/assets/runtime-tools-settings-panel-Bv-akndY.js +0 -5
  246. package/dist/gateway/static/root/assets/sessions-page-D2wmGNZE.js +0 -1
  247. package/dist/gateway/static/root/assets/settings-advanced-gate-CYCCUMEt.js +0 -1
  248. package/dist/gateway/static/root/assets/shares-settings-rf8f1OGq.js +0 -1
  249. package/dist/gateway/static/root/assets/skill-reload-api-BkvclZ_o.js +0 -1
  250. package/dist/gateway/static/root/assets/skills-page.utils-DGjnz-NG.js +0 -1
  251. package/dist/gateway/static/root/assets/task-detail-page-6a2RdDl2.js +0 -1
  252. package/dist/gateway/static/root/assets/tunnel-api-Chfiba_x.js +0 -1
  253. package/dist/gateway/static/root/assets/user-context-page-SeOHP6XO.js +0 -1
  254. package/dist/gateway/static/root/assets/voice-config-api-BO6A8V3Z.js +0 -1
  255. package/dist/gateway/static/root/assets/work-discovery-overlay-BfwEoOGL.js +0 -1
  256. package/dist/gateway/static/root/assets/workflow-run-setup-panel-X7Z5_lRX.js +0 -3
  257. package/dist/gateway/static/root/assets/workflows-page-BklMzkg8.js +0 -5
@@ -8,6 +8,7 @@ import { init_public_url, validatePublicUrl } from "./public-url.js";
8
8
  import { TelegramAccountConfigSchema, TelegramConfigSchema, TelegramGroupConfigSchema, TelegramTopicConfigSchema, init_config_schema } from "../../extensions/telegram/src/config-schema.js";
9
9
  import { WeixinAccountConfigSchema, WeixinConfigSchema, init_config_schema as init_config_schema$1 } from "../../extensions/weixin/src/config-schema.js";
10
10
  import { z } from "zod";
11
+ import semver from "semver";
11
12
  //#region src/config/schema.ts
12
13
  function getAgentDefaultModelRef(config) {
13
14
  return config.agents.list.find((entry) => entry.enabled !== false && entry.id === config.agents.default)?.models?.chat?.primary ?? config.agents.defaults.models.chat.primary;
@@ -36,7 +37,7 @@ function parseModelRef(ref) {
36
37
  model: trimmed.slice(idx + 1).trim()
37
38
  };
38
39
  }
39
- var AgentModelRefSchema, AgentImageGenerationModelSchema, AgentModelsSchema, AgentsConfigSchema, BrowserCloudConfigSchema, BrowserExtensionConfigSchema, BrowserCloakConfigSchema, BrowserConfigSchema, BindingMatchSchema, BindingRuleSchema, BindingsConfigSchema, SessionDmScopeSchema, SessionStorageConfigSchema, SessionResetModeSchema, SessionResetConfigSchema, SessionResetByTypeSchema, SessionScopeSchema, SessionConfigSchema, ChannelsConfigSchema, SearchProviderEntrySchema, WebSearchConfigSchema, WebsiteBlocklistSchema, WebToolsConfigSchema, ToolsConfigSchema, RuntimePreferenceSchema, RuntimeProvisionSchema, LanguageRuntimeSchema, DEFAULT_RUNTIME_TOOLS_CONFIG, RuntimeToolsConfigSchema, GatewayAuthRateLimitSchema, GatewaySecuritySchema, GatewayTrustedProxySchema, GatewayAuthSchema, GatewayTailscaleConsentSchema, GatewayTailscaleSchema, GatewayRemoteSchema, GatewayTlsSchema, GatewayModeSchema, HeartbeatConfigSchema, GatewayChannelConnectDeferModeSchema, TunnelConsentSchema, TunnelConfigSchema, WorkspaceImportConfigSchema, WorkspaceConfigSchema, GatewayBindModeSchema, GatewayWebchatConfigSchema, GatewayConfigSchema, ModelsDevConfigSchema, ModelCatalogConfigSchema, SttProviderConfigCatchallSchema, STTProviderConfigSchema, STTFallbackConfigSchema, MediaUnderstandingCapabilitiesSchema, MediaUnderstandingModelSchema, STTConfigSchema, TtsProviderConfigCatchallSchema, TTSProviderConfigSchema, TTSFallbackConfigSchema, TTSModelOverridesConfigSchema, TTSEdgeConfigSchema, TTSSummarizationConfigSchema, TTSConfigSchema, VoiceRefinementConfigSchema, VoiceConfigSchema, MessagesConfigSchema, ToolsMediaAudioConfigSchema, ToolsMediaConfigSchema, ProviderAzureConfigSchema, ProviderRequestOverridesSchema, ProviderAuthConfigSchema, ProvidersConfigSchema, ExtensionSecurityConfigSchema, ExtensionSlotsConfigSchema, ExtensionsConfigSchema, UpdateAutoConfigSchema, UpdateConfigSchema, CommandsConfigSchema, TuiConfigSchema, McpHttpUrlSchema, ConnectorSecretReferenceSchema, McpConfigScalarSchema, McpOAuthConfigSchema, McpServerSchema, McpConfigSchema, ConnectorsConfigSchema, ExperimentalConfigSchema, ConfigSchema;
40
+ var AgentModelRefSchema, AgentImageGenerationModelSchema, AgentModelsSchema, AgentsConfigSchema, BrowserCloudConfigSchema, BrowserExtensionConfigSchema, BrowserCloakConfigSchema, BrowserConfigSchema, BindingMatchSchema, BindingRuleSchema, BindingsConfigSchema, SessionDmScopeSchema, SessionStorageConfigSchema, SessionResetModeSchema, SessionResetConfigSchema, SessionResetByTypeSchema, SessionScopeSchema, SessionConfigSchema, ChannelsConfigSchema, SearchProviderEntrySchema, WebSearchConfigSchema, WebsiteBlocklistSchema, WebToolsConfigSchema, ToolsConfigSchema, RuntimePreferenceSchema, RuntimeProvisionSchema, RuntimeVersionRequestSchema, LanguageRuntimeSchema, DEFAULT_RUNTIME_TOOLS_CONFIG, RuntimeToolsConfigSchema, GatewayAuthRateLimitSchema, GatewaySecuritySchema, GatewayTrustedProxySchema, GatewayAuthSchema, GatewayTailscaleConsentSchema, GatewayTailscaleSchema, GatewayRemoteSchema, GatewayTlsSchema, GatewayModeSchema, HeartbeatConfigSchema, GatewayChannelConnectDeferModeSchema, TunnelConsentSchema, TunnelConfigSchema, WorkspaceImportConfigSchema, WorkspaceConfigSchema, GatewayBindModeSchema, GatewayWebchatConfigSchema, GatewayConfigSchema, ModelsDevConfigSchema, ModelCatalogConfigSchema, SttProviderConfigCatchallSchema, STTProviderConfigSchema, STTFallbackConfigSchema, MediaUnderstandingCapabilitiesSchema, MediaUnderstandingModelSchema, STTConfigSchema, TtsProviderConfigCatchallSchema, TTSProviderConfigSchema, TTSFallbackConfigSchema, TTSModelOverridesConfigSchema, TTSEdgeConfigSchema, TTSSummarizationConfigSchema, TTSConfigSchema, VoiceRefinementConfigSchema, VoiceConfigSchema, MessagesConfigSchema, ToolsMediaAudioConfigSchema, ToolsMediaConfigSchema, ProviderAzureConfigSchema, ProviderRequestOverridesSchema, ProviderAuthConfigSchema, ProvidersConfigSchema, ExtensionSecurityConfigSchema, ExtensionSlotsConfigSchema, ExtensionsConfigSchema, UpdateAutoConfigSchema, UpdateConfigSchema, CommandsConfigSchema, TuiConfigSchema, McpHttpUrlSchema, ConnectorSecretReferenceSchema, McpConfigScalarSchema, McpOAuthConfigSchema, McpServerSchema, McpConfigSchema, ConnectorsConfigSchema, ExperimentalConfigSchema, ConfigSchema;
40
41
  var init_schema = __esmMin((() => {
41
42
  init_agent_config();
42
43
  init_cache_dir_policy();
@@ -240,9 +241,10 @@ var init_schema = __esmMin((() => {
240
241
  "on-demand",
241
242
  "disabled"
242
243
  ]);
244
+ RuntimeVersionRequestSchema = z.string().trim().min(1).max(128).refine((value) => !value.includes("/") && !value.includes("\\") && !value.includes("\0"), "Runtime version must not contain path separators").refine((value) => semver.validRange(value) !== null, "Runtime version must be a valid SemVer version or range");
243
245
  LanguageRuntimeSchema = z.object({
244
246
  enabled: z.boolean().default(true),
245
- version: z.string().min(1).optional(),
247
+ version: RuntimeVersionRequestSchema.optional(),
246
248
  preference: RuntimePreferenceSchema.default("managed-first"),
247
249
  provision: RuntimeProvisionSchema.default("on-demand")
248
250
  });
@@ -280,7 +282,7 @@ var init_schema = __esmMin((() => {
280
282
  }),
281
283
  uv: z.object({
282
284
  enabled: z.boolean().default(true),
283
- version: z.string().min(1).optional()
285
+ version: RuntimeVersionRequestSchema.optional()
284
286
  }).default({ enabled: true }),
285
287
  download: z.object({
286
288
  bundleDir: z.string().min(1).optional(),
@@ -798,7 +800,37 @@ activityDetailDefault: z.enum([
798
800
  VoiceConfigSchema = z.object({
799
801
  languageMode: z.enum(["auto", "manual"]).optional(),
800
802
  language: z.enum(["en", "zh"]).optional(),
801
- input: z.object({ refinement: VoiceRefinementConfigSchema.optional() }).strict().optional()
803
+ input: z.object({ refinement: VoiceRefinementConfigSchema.optional() }).strict().optional(),
804
+ realtime: z.object({
805
+ enabled: z.boolean().default(false),
806
+ defaultEngine: z.enum(["agent", "omni"]).default("agent"),
807
+ silenceDurationMs: z.number().int().min(300).max(2e3).default(700),
808
+ idleTimeoutMs: z.number().int().min(1e4).max(3e5).default(6e4),
809
+ maxDictationMs: z.number().int().min(1e4).max(36e5).default(6e5),
810
+ maxConversationMs: z.number().int().min(1e4).max(72e5).default(36e5),
811
+ bargeIn: z.boolean().default(true),
812
+ /** Conversation output selection; credentials stay in the provider configuration. */
813
+ tts: z.object({
814
+ provider: z.enum(["alibaba", "xopc-cloud"]),
815
+ voice: z.string().trim().min(1).max(200).optional()
816
+ }).strict().optional(),
817
+ omni: z.object({
818
+ provider: z.enum(["alibaba", "xopc-cloud"]),
819
+ model: z.string().min(1).max(200),
820
+ voice: z.string().min(1).max(100),
821
+ baseUrl: z.string().url().optional(),
822
+ apiKey: z.string().min(1).optional(),
823
+ instructions: z.string().max(8e3).default("You are a friendly voice companion. Keep replies conversational and concise. You cannot execute tools or perform actions.")
824
+ }).strict().optional()
825
+ }).strict().default({
826
+ enabled: false,
827
+ defaultEngine: "agent",
828
+ silenceDurationMs: 700,
829
+ idleTimeoutMs: 6e4,
830
+ maxDictationMs: 6e5,
831
+ maxConversationMs: 36e5,
832
+ bargeIn: true
833
+ })
802
834
  }).strict().optional();
803
835
  MessagesConfigSchema = z.object({
804
836
  /** Voice (text-to-speech) output configuration. */
@@ -8,8 +8,8 @@ import { collectExtensionPackageDependencyIssues } from "./package-contract.js";
8
8
  import { dirname, isAbsolute, join, resolve, sep } from "path";
9
9
  import { cpSync, existsSync, mkdirSync, mkdtempSync, readFileSync, readdirSync, rmSync, writeFileSync } from "fs";
10
10
  import { execFileSync } from "node:child_process";
11
- import AdmZip from "adm-zip";
12
11
  import semver from "semver";
12
+ import AdmZip from "adm-zip";
13
13
  import { tmpdir } from "os";
14
14
  //#region src/extensions/install.ts
15
15
  /**
@@ -40,5 +40,6 @@ export declare class FileSpaceService {
40
40
  resource: FileResource;
41
41
  absolutePath: string;
42
42
  }>;
43
+ rootResource(spaceId: string): Promise<FileResource>;
43
44
  children(spaceId: string, path?: string): Promise<FileResource[]>;
44
45
  }
@@ -289,6 +289,10 @@ var FileSpaceService = class {
289
289
  absolutePath
290
290
  };
291
291
  }
292
+ async rootResource(spaceId) {
293
+ const space = await this.get(spaceId);
294
+ return fileResourceFromPath(space, await resolveFilePath(space.root, ""));
295
+ }
292
296
  async children(spaceId, path = "") {
293
297
  const space = await this.get(spaceId);
294
298
  const directory = await resolveFilePath(space.root, path);
@@ -35,7 +35,12 @@ async function* coalesceThinkingDeltas(source, options = {}) {
35
35
  if (!Number.isFinite(windowMs) || windowMs <= 0) throw new Error("thinking delta coalescer windowMs must be greater than zero");
36
36
  if (!Number.isInteger(maxChars) || maxChars <= 0) throw new Error("thinking delta coalescer maxChars must be a positive integer");
37
37
  const iterator = source[Symbol.asyncIterator]();
38
- let next = iterator.next();
38
+ const readNext = () => {
39
+ const result = iterator.next();
40
+ result.catch(() => {});
41
+ return result;
42
+ };
43
+ let next = readNext();
39
44
  let pending;
40
45
  let deadlineAt = 0;
41
46
  try {
@@ -43,7 +48,7 @@ async function* coalesceThinkingDeltas(source, options = {}) {
43
48
  if (!pending) {
44
49
  const result = await next;
45
50
  if (result.done) break;
46
- next = iterator.next();
51
+ next = readNext();
47
52
  if (!isThinkingDelta(result.value)) {
48
53
  yield result.value;
49
54
  continue;
@@ -68,7 +73,7 @@ async function* coalesceThinkingDeltas(source, options = {}) {
68
73
  pending = void 0;
69
74
  break;
70
75
  }
71
- next = iterator.next();
76
+ next = readNext();
72
77
  const event = result.value;
73
78
  if (!isThinkingDelta(event) || !belongsToSameThinkingStream(pending, event)) {
74
79
  yield pending;
@@ -274,17 +274,7 @@ export declare function buildSafeWebConfigPayload(service: GatewayService, optio
274
274
  };
275
275
  stt: unknown;
276
276
  tts: unknown;
277
- voice: {
278
- languageMode?: "manual" | "auto";
279
- language?: "en" | "zh";
280
- input?: {
281
- refinement?: {
282
- mode: "off" | "custom" | "punctuation" | "light";
283
- model?: string;
284
- customInstruction?: string;
285
- };
286
- };
287
- };
277
+ voice: unknown;
288
278
  tools: {
289
279
  web: {
290
280
  region: "cn" | "global" | null;
@@ -13,7 +13,7 @@ import { GENERIC_MASKED_SECRET, maskSecretLength } from "./mask-secret-length.js
13
13
  import { safeToolsWebForGet } from "../../config-tools-web.js";
14
14
  import { maskTunnelSecretForWeb } from "../../../tunnel/env.js";
15
15
  import { buildSafeProvidersConfigForWeb } from "./safe-providers-config.js";
16
- import { maskSttConfigForWeb, maskTtsConfigForWeb } from "./safe-voice-config.js";
16
+ import { maskRealtimeVoiceConfigForWeb, maskSttConfigForWeb, maskTtsConfigForWeb } from "./safe-voice-config.js";
17
17
  //#region src/gateway/hono/lib/config-payload.ts
18
18
  init_agent_scope();
19
19
  init_channel_catalog_service();
@@ -195,7 +195,7 @@ async function buildSafeWebConfigPayload(service, options = {}) {
195
195
  update: { ...resolveUpdateConfigForWeb(config) },
196
196
  stt: maskSttConfigForWeb(config.tools?.media?.audio),
197
197
  tts: maskTtsConfigForWeb(config.messages?.tts),
198
- voice: config.voice,
198
+ voice: maskRealtimeVoiceConfigForWeb(config.voice),
199
199
  tools: safeToolsWebForGet(config),
200
200
  bindings: Array.isArray(config.bindings) ? config.bindings : [],
201
201
  mcp: buildSafeMcpConfigForWeb(config)
@@ -1,3 +1,17 @@
1
+ export declare function maskRealtimeVoiceConfigForWeb(voice: {
2
+ realtime?: {
3
+ omni?: {
4
+ apiKey?: string;
5
+ };
6
+ };
7
+ } | undefined): unknown;
8
+ export declare function mergeRealtimeVoiceConfigPatch(previous: {
9
+ realtime?: {
10
+ omni?: {
11
+ apiKey?: string;
12
+ };
13
+ };
14
+ } | undefined, incoming: unknown): unknown;
1
15
  /** Mask STT api keys for GET `/api/config`. */
2
16
  export declare function maskSttConfigForWeb(stt: unknown): unknown;
3
17
  /** Mask TTS api keys for GET `/api/config`. */
@@ -1,6 +1,34 @@
1
1
  import { maskSecretLength } from "./mask-secret-length.js";
2
2
  import { isMaskedApiKey } from "../../config-tools-web.js";
3
3
  //#region src/gateway/hono/lib/safe-voice-config.ts
4
+ function maskRealtimeVoiceConfigForWeb(voice) {
5
+ if (!voice?.realtime?.omni) return voice;
6
+ return {
7
+ ...voice,
8
+ realtime: {
9
+ ...voice.realtime,
10
+ omni: maskProviderSlice(voice.realtime.omni)
11
+ }
12
+ };
13
+ }
14
+ function mergeRealtimeVoiceConfigPatch(previous, incoming) {
15
+ if (!incoming || typeof incoming !== "object" || Array.isArray(incoming)) return incoming;
16
+ const patch = incoming;
17
+ const realtime = patch.realtime;
18
+ const omni = realtime?.omni;
19
+ if (!omni || typeof omni !== "object" || Array.isArray(omni)) return incoming;
20
+ const apiKey = omni.apiKey === "" ? void 0 : mergeApiKeyField(omni.apiKey, previous?.realtime?.omni?.apiKey);
21
+ return {
22
+ ...patch,
23
+ realtime: {
24
+ ...realtime,
25
+ omni: {
26
+ ...omni,
27
+ ...omni.apiKey !== void 0 ? { apiKey } : {}
28
+ }
29
+ }
30
+ };
31
+ }
4
32
  function maskProviderSlice(slice) {
5
33
  const next = { ...slice };
6
34
  if (typeof next.apiKey === "string" && next.apiKey.trim()) next.apiKey = maskSecretLength(next.apiKey);
@@ -64,4 +92,4 @@ function mergeTtsConfigPatch(previous, incoming) {
64
92
  return mergeVoiceConfigPatch(previous, incoming);
65
93
  }
66
94
  //#endregion
67
- export { maskSttConfigForWeb, maskTtsConfigForWeb, mergeSttConfigPatch, mergeTtsConfigPatch };
95
+ export { maskRealtimeVoiceConfigForWeb, maskSttConfigForWeb, maskTtsConfigForWeb, mergeRealtimeVoiceConfigPatch, mergeSttConfigPatch, mergeTtsConfigPatch };
@@ -9,7 +9,7 @@ import { isMaskedSecretPatchValue } from "../../lib/mask-secret-length.js";
9
9
  import { applyToolsWebPatch } from "../../../config-tools-web.js";
10
10
  import { mergeTunnelConfigPatch } from "../../../../tunnel/tunnel-config.js";
11
11
  import { assertGatewayRuntimeConfig } from "../../../runtime-config.js";
12
- import { mergeSttConfigPatch, mergeTtsConfigPatch } from "../../lib/safe-voice-config.js";
12
+ import { mergeRealtimeVoiceConfigPatch, mergeSttConfigPatch, mergeTtsConfigPatch } from "../../lib/safe-voice-config.js";
13
13
  import { PATCH_OK, patchError } from "./result.js";
14
14
  //#region src/gateway/hono/routes/config-patch/misc.ts
15
15
  init_schema();
@@ -137,7 +137,7 @@ async function applyMiscPatch(config, body) {
137
137
  config.messages.tts = mergeTtsConfigPatch(config.messages.tts, body.tts);
138
138
  }
139
139
  if (body.voice !== void 0) {
140
- const parsed = VoiceConfigSchema.safeParse(body.voice);
140
+ const parsed = VoiceConfigSchema.safeParse(mergeRealtimeVoiceConfigPatch(config.voice, body.voice));
141
141
  if (!parsed.success) return patchError(parsed.error.issues.map((i) => i.message).join("; "));
142
142
  config.voice = parsed.data;
143
143
  }
@@ -86,6 +86,13 @@ function registerFilesRoutes(authenticated, deps) {
86
86
  return errorResponse(c, error);
87
87
  }
88
88
  });
89
+ authenticated.get("/api/files/spaces/:id/root", async (c) => {
90
+ try {
91
+ return c.json({ resource: await files.rootResource(c.req.param("id")) });
92
+ } catch (error) {
93
+ return errorResponse(c, error);
94
+ }
95
+ });
89
96
  authenticated.get("/api/files/recent", async (c) => {
90
97
  try {
91
98
  const limit = Math.min(100, Math.max(1, Number(c.req.query("limit")) || 50));
@@ -3,6 +3,16 @@ import { APP_LAZY_ROUTE_BUNDLES, AUTHENTICATED_LAZY_ROUTE_BUNDLES, findAuthentic
3
3
  import { Hono } from "hono";
4
4
  //#region src/gateway/hono/routes/lazy-fallback.ts
5
5
  const log = createGatewayRouteLogger("LazyRoutes");
6
+ const FORWARDED_VARIABLES = Symbol("gateway.forwardedVariables");
7
+ function createSubApp() {
8
+ const sub = new Hono();
9
+ sub.use(async (c, next) => {
10
+ const variables = c.env?.[FORWARDED_VARIABLES];
11
+ for (const [key, value] of Object.entries(variables ?? {})) c.set(key, value);
12
+ await next();
13
+ });
14
+ return sub;
15
+ }
6
16
  const authenticatedSubApps = /* @__PURE__ */ new Map();
7
17
  const appSubApps = /* @__PURE__ */ new Map();
8
18
  const authenticatedLoadPromises = /* @__PURE__ */ new Map();
@@ -28,7 +38,7 @@ async function ensureAuthenticatedLazyBundle(bundleId, deps) {
28
38
  if (!bundle) return null;
29
39
  pending = (async () => {
30
40
  const mod = await bundle.load();
31
- const sub = new Hono();
41
+ const sub = createSubApp();
32
42
  mod.register(sub, deps);
33
43
  authenticatedSubApps.set(bundleId, sub);
34
44
  authenticatedLoadPromises.delete(bundleId);
@@ -47,7 +57,7 @@ async function ensureAppLazyBundle(bundleId, params) {
47
57
  if (!bundle) return null;
48
58
  pending = (async () => {
49
59
  const mod = await bundle.load();
50
- const sub = new Hono();
60
+ const sub = createSubApp();
51
61
  if (mod.registerOnApp) mod.registerOnApp(sub, params.service);
52
62
  appSubApps.set(bundleId, sub);
53
63
  appLoadPromises.delete(bundleId);
@@ -58,10 +68,14 @@ async function ensureAppLazyBundle(bundleId, params) {
58
68
  return pending;
59
69
  }
60
70
  async function forwardToSubApp(c, sub) {
71
+ const env = {
72
+ ...c.env,
73
+ [FORWARDED_VARIABLES]: { ...c.var }
74
+ };
61
75
  try {
62
- return await sub.fetch(c.req.raw, c.env, c.executionCtx);
76
+ return await sub.fetch(c.req.raw, env, c.executionCtx);
63
77
  } catch (error) {
64
- if (error instanceof Error && error.message.includes("ExecutionContext")) return sub.fetch(c.req.raw, c.env);
78
+ if (error instanceof Error && error.message.includes("ExecutionContext")) return sub.fetch(c.req.raw, env);
65
79
  logRouteError(log, c, error, "gateway.route.lazy_forward");
66
80
  throw error;
67
81
  }
@@ -1,5 +1,6 @@
1
1
  import { init_paths_state, resolveStateDir } from "../../../config/paths-state.js";
2
2
  import { RuntimeToolsConfigSchema, init_schema } from "../../../config/schema.js";
3
+ import { normalizeRuntimeVersionRequest } from "../../../runtime-tools/probe.js";
3
4
  import { ManagedRuntimeManager } from "../../../runtime-tools/manager.js";
4
5
  import { createGatewayRouteLogger } from "../lib/route-logger.js";
5
6
  import { pruneRuntimeTools } from "../../../runtime-tools/prune.js";
@@ -82,6 +83,11 @@ function registerRuntimeToolsRoutes(authenticated, deps) {
82
83
  }, 400);
83
84
  const body = await readJson(c);
84
85
  const version = typeof body.version === "string" && body.version.trim() ? body.version.trim() : void 0;
86
+ if (version && !normalizeRuntimeVersionRequest(version)) return c.json({
87
+ ok: false,
88
+ error: "invalid-version",
89
+ message: "Invalid runtime version"
90
+ }, 400);
85
91
  return streamSSE(c, async (stream) => {
86
92
  const manager = runtimeManager(service.currentConfig);
87
93
  let writes = Promise.resolve();
@@ -97,7 +103,7 @@ function registerRuntimeToolsRoutes(authenticated, deps) {
97
103
  };
98
104
  manager.on("progress", onProgress);
99
105
  try {
100
- const resolved = action === "repair" ? await manager.repair(runtime) : await manager.install(runtime, version);
106
+ const resolved = action === "repair" ? await manager.repair(runtime, version) : await manager.install(runtime, version);
101
107
  await writes;
102
108
  await stream.writeSSE({
103
109
  event: "result",
@@ -73,6 +73,13 @@ async function submitSessionInput(c, deps, sessionKey) {
73
73
  }
74
74
  }, 400);
75
75
  return withModelConfigLock(sessionKey, async () => {
76
+ if (deps.service.voiceRealtime?.hasConversation(sessionKey)) return c.json({
77
+ ok: false,
78
+ error: {
79
+ code: "SESSION_BUSY",
80
+ message: "End the voice call before sending text"
81
+ }
82
+ }, 409);
76
83
  const selection = body.configVersion !== void 0 ? await deps.service.sessions.getAgentConfig(sessionKey) : void 0;
77
84
  if (selection) {
78
85
  if (!Number.isSafeInteger(body.configVersion) || selection.configVersion !== body.configVersion || !selection.fixedModel) return c.json({
@@ -181,6 +188,13 @@ async function replaceLatestSessionTurn(c, deps, sessionKey, targetTurnId) {
181
188
  }
182
189
  }, 401);
183
190
  return withModelConfigLock(sessionKey, async () => {
191
+ if (deps.service.voiceRealtime?.hasConversation(sessionKey)) return c.json({
192
+ ok: false,
193
+ error: {
194
+ code: "SESSION_BUSY",
195
+ message: "End the voice call before editing a turn"
196
+ }
197
+ }, 409);
184
198
  const selection = body.configVersion !== void 0 ? await deps.service.sessions.getAgentConfig(sessionKey) : void 0;
185
199
  if (selection) {
186
200
  if (!Number.isSafeInteger(body.configVersion) || selection.configVersion !== body.configVersion || !selection.fixedModel) return c.json({
@@ -3,13 +3,13 @@ import { resolveProjectAgentId } from "../../../projects/project-agent.js";
3
3
  import "../../../projects/index.js";
4
4
  import { evictEmbeddedSessionRunner } from "../../../agent/embedded/session-runner.js";
5
5
  import { messagesToClientHistory } from "../../../session/client-history.js";
6
- import { SessionEnvironmentService } from "../../../execution-environments/session-environment-service.js";
7
6
  import { deleteMediaUrisNoLongerReferenced } from "../../../media/session-references.js";
8
7
  import { getGatewayPrincipal } from "../../security/gateway-principal.js";
9
8
  import { createGatewayRouteLogger, logRouteError } from "../lib/route-logger.js";
10
9
  import { patchChatModelConfig } from "./chat-model-config.js";
11
10
  import { getSessionContextSummary } from "../../session-context-summary.js";
12
11
  import { respondStartupUnavailable } from "../lib/startup-unavailable.js";
12
+ import { SessionEnvironmentService } from "../../../execution-environments/session-environment-service.js";
13
13
  import { randomUUID } from "node:crypto";
14
14
  //#region src/gateway/hono/routes/sessions.ts
15
15
  init_session_key();
@@ -785,6 +785,7 @@ function registerSessionsRoutes(authenticated, deps) {
785
785
  });
786
786
  authenticated.delete("/api/sessions/:key/messages", async (c) => {
787
787
  const key = c.req.param("key");
788
+ if (service.voiceRealtime?.hasConversation(key)) return c.json({ error: "End the voice call before editing its history" }, 409);
788
789
  const body = await c.req.json().catch(() => ({}));
789
790
  const userRoundIndex = typeof body.userRoundIndex === "number" ? body.userRoundIndex : void 0;
790
791
  if (userRoundIndex === void 0 || !Number.isInteger(userRoundIndex) || userRoundIndex < 0) return c.json({ error: "userRoundIndex must be a non-negative integer" }, 400);
@@ -805,6 +806,7 @@ function registerSessionsRoutes(authenticated, deps) {
805
806
  const blocked = ensureGatewayReadyForSessions(c, service, "sessions.reset");
806
807
  if (blocked) return blocked;
807
808
  const key = c.req.param("key");
809
+ if (service.voiceRealtime?.hasConversation(key)) return c.json({ error: "End the voice call before resetting the session" }, 409);
808
810
  const result = await service.sessions.reset(key);
809
811
  if (result.ok === false) {
810
812
  const status = result.error === "Session not found" ? 404 : 400;
@@ -824,6 +826,7 @@ function registerSessionsRoutes(authenticated, deps) {
824
826
  });
825
827
  authenticated.delete("/api/sessions/:key", async (c) => {
826
828
  const key = c.req.param("key");
829
+ if (service.voiceRealtime?.hasConversation(key)) return c.json({ error: "End the voice call before deleting the session" }, 409);
827
830
  if (environments.get(key) && service.getActiveWebchatRunId(key)) return c.json({
828
831
  ok: false,
829
832
  error: "Stop the active session run before deleting its environment"
@@ -2,7 +2,7 @@ import { getDefaultModelSync, init_providers, resolveModel } from "../../../prov
2
2
  import { completeWithResolvedCredentials } from "../../../providers/model-call.js";
3
3
  import { resolveTtsProviderConfigSlice } from "../../../voice/tts/config-slice.js";
4
4
  import { isTTSAvailable, resolveSpeechProvider } from "../../../voice/tts/factory.js";
5
- import { speak } from "../../../voice/tts/speak-core.js";
5
+ import { speak, speakStream } from "../../../voice/tts/speak-core.js";
6
6
  import { mergeTtsConfigFromAppConfig } from "../../../voice/tts/merge-config.js";
7
7
  import { getLocalVoiceRuntimeClient } from "../../../voice/local/runtime-client.js";
8
8
  import { getAudioDecoderStatus } from "../../../voice/audio/normalize.js";
@@ -13,9 +13,14 @@ import { mergeSttConfigFromAppConfig } from "../../../voice/stt/config.js";
13
13
  import "../../../voice/stt/index.js";
14
14
  import { listSttProvidersForApi } from "../../../voice/stt/list-providers.js";
15
15
  import "../../../voice/tts/index.js";
16
+ import { withModelConfigLock } from "../../../session/model-config-lock.js";
17
+ import { createVoiceSessionRequestSchema } from "../../../../packages/realtime-protocol/src/voice.js";
18
+ import { resolveOmniRoute } from "../../../voice/realtime/omniRoute.js";
19
+ import { VoiceSessionCreationError, resolveStreamingStt, resolveStreamingTts } from "../../../voice/realtime/runtime.js";
20
+ import { getGatewayPrincipal } from "../../security/gateway-principal.js";
16
21
  import { createGatewayRouteLogger } from "../lib/route-logger.js";
17
- import { listTtsProvidersForApi } from "../../../voice/tts/list-providers.js";
18
22
  import { listLocalVoiceModelStatuses, removeLocalVoiceModel, startLocalVoiceModelInstall } from "../../../voice/local/model-manager.js";
23
+ import { listTtsProvidersForApi } from "../../../voice/tts/list-providers.js";
19
24
  //#region src/gateway/hono/routes/voice.ts
20
25
  init_providers();
21
26
  const log = createGatewayRouteLogger("Voice");
@@ -107,6 +112,134 @@ async function refineTranscript(raw, config, signal) {
107
112
  }
108
113
  function registerVoiceRoutes(authenticated, deps) {
109
114
  const { service, strictRateLimitMiddleware } = deps;
115
+ authenticated.get("/api/voice/realtime/status", async (c) => {
116
+ const config = service.currentConfig;
117
+ const stt = resolveStreamingStt(config);
118
+ const tts = resolveStreamingTts(config);
119
+ const omni = await resolveOmniRoute(config).catch(() => null);
120
+ const enabled = config.voice?.realtime?.enabled === true;
121
+ const availability = (configured) => ({
122
+ available: enabled && configured,
123
+ ...!enabled ? { reasonCode: "VOICE_DISABLED" } : !configured ? { reasonCode: "PROVIDER_UNAVAILABLE" } : {}
124
+ });
125
+ return c.json({
126
+ ok: true,
127
+ payload: {
128
+ enabled,
129
+ capabilities: {
130
+ dictation: availability(Boolean(stt)),
131
+ agent: availability(Boolean(stt && tts)),
132
+ omni: availability(Boolean(omni)),
133
+ languages: ["zh", "en"],
134
+ bargeIn: config.voice?.realtime?.bargeIn ?? true
135
+ },
136
+ defaultEngine: config.voice?.realtime?.defaultEngine ?? "agent",
137
+ omni: omni?.route ?? null,
138
+ stt: stt?.route ?? null,
139
+ tts: tts ? {
140
+ ...tts.route,
141
+ voice: tts.config.providers?.[tts.route.provider]?.voice ?? tts.provider.providerConfig.voice
142
+ } : null
143
+ }
144
+ });
145
+ });
146
+ authenticated.post("/api/voice/realtime/preview", strictRateLimitMiddleware, async (c) => {
147
+ const config = service.currentConfig;
148
+ const route = resolveStreamingTts(config);
149
+ if (!route) return c.json({
150
+ ok: false,
151
+ error: { message: "Realtime voice output is not configured" }
152
+ }, 503);
153
+ const controller = new AbortController();
154
+ const signal = AbortSignal.any([
155
+ c.req.raw.signal,
156
+ controller.signal,
157
+ AbortSignal.timeout(2e4)
158
+ ]);
159
+ let result;
160
+ let reader;
161
+ try {
162
+ result = await speakStream(config.voice?.language === "en" ? "Hello, I am your assistant. You can talk to me naturally." : "你好,我是你的助手。现在可以和我自然对话了。", route.config, {
163
+ signal,
164
+ appConfig: config,
165
+ allowFallback: false,
166
+ parseDirectives: false
167
+ });
168
+ if (result.outputFormat !== "pcm") throw new Error("Realtime preview requires PCM audio");
169
+ reader = result.audioStream.getReader();
170
+ const chunks = [];
171
+ let size = 0;
172
+ while (true) {
173
+ signal.throwIfAborted();
174
+ const { value, done } = await reader.read();
175
+ if (done) break;
176
+ size += value.byteLength;
177
+ if (size > 96e4) throw new Error("Realtime preview audio exceeds the limit");
178
+ chunks.push(value);
179
+ }
180
+ if (size === 0 || size % 2 !== 0) throw new Error("Realtime preview returned invalid audio");
181
+ return c.json({
182
+ ok: true,
183
+ payload: {
184
+ audio: Buffer.concat(chunks).toString("base64"),
185
+ sampleRate: 24e3
186
+ }
187
+ });
188
+ } catch (error) {
189
+ log.warn({
190
+ err: error,
191
+ provider: route.route.provider
192
+ }, "Realtime voice preview failed");
193
+ return c.json({
194
+ ok: false,
195
+ error: { message: "Voice preview failed. Check the provider credentials and try again." }
196
+ }, 502);
197
+ } finally {
198
+ controller.abort();
199
+ await reader?.cancel().catch(() => void 0);
200
+ reader?.releaseLock();
201
+ await result?.release();
202
+ }
203
+ });
204
+ for (const action of ["preflight", "sessions"]) authenticated.post(`/api/voice/realtime/${action}`, strictRateLimitMiddleware, async (c) => {
205
+ const parsed = createVoiceSessionRequestSchema.safeParse(await c.req.json().catch(() => null));
206
+ if (!parsed.success) return c.json({
207
+ ok: false,
208
+ error: {
209
+ code: "INVALID_REQUEST",
210
+ message: "Invalid realtime voice session request"
211
+ }
212
+ }, 400);
213
+ try {
214
+ if (action === "preflight") {
215
+ await service.voiceRealtime.preflight(parsed.data);
216
+ return c.json({ ok: true });
217
+ }
218
+ const principal = getGatewayPrincipal(c);
219
+ const create = () => service.voiceRealtime.createSession(parsed.data, principal.principalId);
220
+ const payload = parsed.data.sessionKey ? await withModelConfigLock(parsed.data.sessionKey, create) : await create();
221
+ return c.json({
222
+ ok: true,
223
+ payload
224
+ });
225
+ } catch (error) {
226
+ const message = error instanceof Error ? error.message : "Realtime voice is unavailable";
227
+ if (error instanceof VoiceSessionCreationError) return c.json({
228
+ ok: false,
229
+ error: {
230
+ code: error.code,
231
+ message
232
+ }
233
+ }, error.status);
234
+ return c.json({
235
+ ok: false,
236
+ error: {
237
+ code: "PROVIDER_UNAVAILABLE",
238
+ message
239
+ }
240
+ }, 503);
241
+ }
242
+ });
110
243
  authenticated.post("/api/voice/language", strictRateLimitMiddleware, async (c) => {
111
244
  let body = {};
112
245
  try {
@@ -153,7 +286,11 @@ function registerVoiceRoutes(authenticated, deps) {
153
286
  error: { message: "provider and model are required" }
154
287
  }, 400);
155
288
  const config = service.currentConfig;
156
- const baseConfig = mergeTtsConfigFromAppConfig(config.messages?.tts);
289
+ const baseConfig = c.req.query("purpose") === "realtime" ? resolveStreamingTts(config)?.config : mergeTtsConfigFromAppConfig(config.messages?.tts);
290
+ if (!baseConfig) return c.json({
291
+ ok: true,
292
+ payload: { voices: [] }
293
+ });
157
294
  const resolved = resolveSpeechProvider(provider, {
158
295
  ...baseConfig,
159
296
  provider,
@@ -68,6 +68,7 @@ var GatewayServer = class {
68
68
  });
69
69
  inner.on("upgrade", (req, socket, head) => {
70
70
  try {
71
+ if (this.service.voiceRealtime.handleUpgrade(req, socket, head)) return;
71
72
  if (this.service.realtime.handleUpgrade(req, socket, head)) return;
72
73
  if (handleSiteShareUpgrade(this.service, req, socket, head)) return;
73
74
  socket.destroy();
@@ -71,6 +71,7 @@ export declare class GatewayAgentRunner {
71
71
  signal?: AbortSignal;
72
72
  runId?: string;
73
73
  sourceContexts?: AgentSourceContext[];
74
+ presentation?: 'voice';
74
75
  }): AsyncGenerator<{
75
76
  type: string;
76
77
  [key: string]: unknown;
@@ -128,12 +128,7 @@ var GatewayAgentRunner = class {
128
128
  completeRealtimeTopic: this.opts.completeRealtimeTopic
129
129
  }, message, channel, chatId, origin, attachments, thinking, runOptions);
130
130
  try {
131
- let step = await iter.next();
132
- while (!step.done) {
133
- yield step.value;
134
- step = await iter.next();
135
- }
136
- return step.value;
131
+ return yield* iter;
137
132
  } finally {
138
133
  if (trackedRunId) {
139
134
  this.resolveRunCompletions.get(trackedRunId)?.();
@@ -25,6 +25,7 @@ export declare function runGatewayAgent(deps: RunGatewayAgentDeps, message: stri
25
25
  signal?: AbortSignal;
26
26
  runId?: string;
27
27
  sourceContexts?: AgentSourceContext[];
28
+ presentation?: 'voice';
28
29
  }): AsyncGenerator<RunGatewayAgentYield, {
29
30
  status: string;
30
31
  summary: string;