@livekit/agents 1.0.48 → 1.1.0-dev.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (373) hide show
  1. package/dist/constants.cjs +27 -0
  2. package/dist/constants.cjs.map +1 -1
  3. package/dist/constants.d.cts +9 -0
  4. package/dist/constants.d.ts +9 -0
  5. package/dist/constants.d.ts.map +1 -1
  6. package/dist/constants.js +18 -0
  7. package/dist/constants.js.map +1 -1
  8. package/dist/inference/api_protos.d.cts +71 -71
  9. package/dist/inference/api_protos.d.ts +71 -71
  10. package/dist/inference/interruption/defaults.cjs +81 -0
  11. package/dist/inference/interruption/defaults.cjs.map +1 -0
  12. package/dist/inference/interruption/defaults.d.cts +19 -0
  13. package/dist/inference/interruption/defaults.d.ts +19 -0
  14. package/dist/inference/interruption/defaults.d.ts.map +1 -0
  15. package/dist/inference/interruption/defaults.js +46 -0
  16. package/dist/inference/interruption/defaults.js.map +1 -0
  17. package/dist/inference/interruption/errors.cjs +44 -0
  18. package/dist/inference/interruption/errors.cjs.map +1 -0
  19. package/dist/inference/interruption/errors.d.cts +12 -0
  20. package/dist/inference/interruption/errors.d.ts +12 -0
  21. package/dist/inference/interruption/errors.d.ts.map +1 -0
  22. package/dist/inference/interruption/errors.js +20 -0
  23. package/dist/inference/interruption/errors.js.map +1 -0
  24. package/dist/inference/interruption/http_transport.cjs +147 -0
  25. package/dist/inference/interruption/http_transport.cjs.map +1 -0
  26. package/dist/inference/interruption/http_transport.d.cts +63 -0
  27. package/dist/inference/interruption/http_transport.d.ts +63 -0
  28. package/dist/inference/interruption/http_transport.d.ts.map +1 -0
  29. package/dist/inference/interruption/http_transport.js +121 -0
  30. package/dist/inference/interruption/http_transport.js.map +1 -0
  31. package/dist/inference/interruption/interruption_cache_entry.cjs +58 -0
  32. package/dist/inference/interruption/interruption_cache_entry.cjs.map +1 -0
  33. package/dist/inference/interruption/interruption_cache_entry.d.cts +30 -0
  34. package/dist/inference/interruption/interruption_cache_entry.d.ts +30 -0
  35. package/dist/inference/interruption/interruption_cache_entry.d.ts.map +1 -0
  36. package/dist/inference/interruption/interruption_cache_entry.js +34 -0
  37. package/dist/inference/interruption/interruption_cache_entry.js.map +1 -0
  38. package/dist/inference/interruption/interruption_detector.cjs +181 -0
  39. package/dist/inference/interruption/interruption_detector.cjs.map +1 -0
  40. package/dist/inference/interruption/interruption_detector.d.cts +59 -0
  41. package/dist/inference/interruption/interruption_detector.d.ts +59 -0
  42. package/dist/inference/interruption/interruption_detector.d.ts.map +1 -0
  43. package/dist/inference/interruption/interruption_detector.js +147 -0
  44. package/dist/inference/interruption/interruption_detector.js.map +1 -0
  45. package/dist/inference/interruption/interruption_stream.cjs +368 -0
  46. package/dist/inference/interruption/interruption_stream.cjs.map +1 -0
  47. package/dist/inference/interruption/interruption_stream.d.cts +46 -0
  48. package/dist/inference/interruption/interruption_stream.d.ts +46 -0
  49. package/dist/inference/interruption/interruption_stream.d.ts.map +1 -0
  50. package/dist/inference/interruption/interruption_stream.js +344 -0
  51. package/dist/inference/interruption/interruption_stream.js.map +1 -0
  52. package/dist/inference/interruption/types.cjs +17 -0
  53. package/dist/inference/interruption/types.cjs.map +1 -0
  54. package/dist/inference/interruption/types.d.cts +66 -0
  55. package/dist/inference/interruption/types.d.ts +66 -0
  56. package/dist/inference/interruption/types.d.ts.map +1 -0
  57. package/dist/inference/interruption/types.js +1 -0
  58. package/dist/inference/interruption/types.js.map +1 -0
  59. package/dist/inference/interruption/utils.cjs +130 -0
  60. package/dist/inference/interruption/utils.cjs.map +1 -0
  61. package/dist/inference/interruption/utils.d.cts +41 -0
  62. package/dist/inference/interruption/utils.d.ts +41 -0
  63. package/dist/inference/interruption/utils.d.ts.map +1 -0
  64. package/dist/inference/interruption/utils.js +105 -0
  65. package/dist/inference/interruption/utils.js.map +1 -0
  66. package/dist/inference/interruption/utils.test.cjs +105 -0
  67. package/dist/inference/interruption/utils.test.cjs.map +1 -0
  68. package/dist/inference/interruption/utils.test.js +104 -0
  69. package/dist/inference/interruption/utils.test.js.map +1 -0
  70. package/dist/inference/interruption/ws_transport.cjs +329 -0
  71. package/dist/inference/interruption/ws_transport.cjs.map +1 -0
  72. package/dist/inference/interruption/ws_transport.d.cts +33 -0
  73. package/dist/inference/interruption/ws_transport.d.ts +33 -0
  74. package/dist/inference/interruption/ws_transport.d.ts.map +1 -0
  75. package/dist/inference/interruption/ws_transport.js +295 -0
  76. package/dist/inference/interruption/ws_transport.js.map +1 -0
  77. package/dist/inference/llm.cjs +14 -10
  78. package/dist/inference/llm.cjs.map +1 -1
  79. package/dist/inference/llm.d.cts +2 -1
  80. package/dist/inference/llm.d.ts +2 -1
  81. package/dist/inference/llm.d.ts.map +1 -1
  82. package/dist/inference/llm.js +8 -10
  83. package/dist/inference/llm.js.map +1 -1
  84. package/dist/inference/stt.cjs +7 -2
  85. package/dist/inference/stt.cjs.map +1 -1
  86. package/dist/inference/stt.d.cts +2 -0
  87. package/dist/inference/stt.d.ts +2 -0
  88. package/dist/inference/stt.d.ts.map +1 -1
  89. package/dist/inference/stt.js +8 -3
  90. package/dist/inference/stt.js.map +1 -1
  91. package/dist/inference/tts.cjs +7 -2
  92. package/dist/inference/tts.cjs.map +1 -1
  93. package/dist/inference/tts.d.cts +2 -0
  94. package/dist/inference/tts.d.ts +2 -0
  95. package/dist/inference/tts.d.ts.map +1 -1
  96. package/dist/inference/tts.js +8 -3
  97. package/dist/inference/tts.js.map +1 -1
  98. package/dist/inference/utils.cjs +26 -7
  99. package/dist/inference/utils.cjs.map +1 -1
  100. package/dist/inference/utils.d.cts +13 -0
  101. package/dist/inference/utils.d.ts +13 -0
  102. package/dist/inference/utils.d.ts.map +1 -1
  103. package/dist/inference/utils.js +18 -2
  104. package/dist/inference/utils.js.map +1 -1
  105. package/dist/llm/chat_context.cjs +20 -2
  106. package/dist/llm/chat_context.cjs.map +1 -1
  107. package/dist/llm/chat_context.d.cts +19 -1
  108. package/dist/llm/chat_context.d.ts +19 -1
  109. package/dist/llm/chat_context.d.ts.map +1 -1
  110. package/dist/llm/chat_context.js +20 -2
  111. package/dist/llm/chat_context.js.map +1 -1
  112. package/dist/llm/index.cjs.map +1 -1
  113. package/dist/llm/index.d.cts +1 -1
  114. package/dist/llm/index.d.ts +1 -1
  115. package/dist/llm/index.d.ts.map +1 -1
  116. package/dist/llm/index.js.map +1 -1
  117. package/dist/llm/llm.cjs +16 -1
  118. package/dist/llm/llm.cjs.map +1 -1
  119. package/dist/llm/llm.d.cts +9 -0
  120. package/dist/llm/llm.d.ts +9 -0
  121. package/dist/llm/llm.d.ts.map +1 -1
  122. package/dist/llm/llm.js +16 -1
  123. package/dist/llm/llm.js.map +1 -1
  124. package/dist/llm/realtime.cjs +3 -0
  125. package/dist/llm/realtime.cjs.map +1 -1
  126. package/dist/llm/realtime.d.cts +1 -0
  127. package/dist/llm/realtime.d.ts +1 -0
  128. package/dist/llm/realtime.d.ts.map +1 -1
  129. package/dist/llm/realtime.js +3 -0
  130. package/dist/llm/realtime.js.map +1 -1
  131. package/dist/metrics/base.cjs.map +1 -1
  132. package/dist/metrics/base.d.cts +45 -1
  133. package/dist/metrics/base.d.ts +45 -1
  134. package/dist/metrics/base.d.ts.map +1 -1
  135. package/dist/metrics/index.cjs +5 -0
  136. package/dist/metrics/index.cjs.map +1 -1
  137. package/dist/metrics/index.d.cts +2 -1
  138. package/dist/metrics/index.d.ts +2 -1
  139. package/dist/metrics/index.d.ts.map +1 -1
  140. package/dist/metrics/index.js +6 -0
  141. package/dist/metrics/index.js.map +1 -1
  142. package/dist/metrics/model_usage.cjs +189 -0
  143. package/dist/metrics/model_usage.cjs.map +1 -0
  144. package/dist/metrics/model_usage.d.cts +92 -0
  145. package/dist/metrics/model_usage.d.ts +92 -0
  146. package/dist/metrics/model_usage.d.ts.map +1 -0
  147. package/dist/metrics/model_usage.js +164 -0
  148. package/dist/metrics/model_usage.js.map +1 -0
  149. package/dist/metrics/model_usage.test.cjs +474 -0
  150. package/dist/metrics/model_usage.test.cjs.map +1 -0
  151. package/dist/metrics/model_usage.test.js +476 -0
  152. package/dist/metrics/model_usage.test.js.map +1 -0
  153. package/dist/metrics/usage_collector.cjs +3 -0
  154. package/dist/metrics/usage_collector.cjs.map +1 -1
  155. package/dist/metrics/usage_collector.d.cts +9 -0
  156. package/dist/metrics/usage_collector.d.ts +9 -0
  157. package/dist/metrics/usage_collector.d.ts.map +1 -1
  158. package/dist/metrics/usage_collector.js +3 -0
  159. package/dist/metrics/usage_collector.js.map +1 -1
  160. package/dist/metrics/utils.cjs +9 -0
  161. package/dist/metrics/utils.cjs.map +1 -1
  162. package/dist/metrics/utils.d.ts.map +1 -1
  163. package/dist/metrics/utils.js +9 -0
  164. package/dist/metrics/utils.js.map +1 -1
  165. package/dist/stream/multi_input_stream.test.cjs +4 -0
  166. package/dist/stream/multi_input_stream.test.cjs.map +1 -1
  167. package/dist/stream/multi_input_stream.test.js +5 -1
  168. package/dist/stream/multi_input_stream.test.js.map +1 -1
  169. package/dist/stream/stream_channel.cjs +31 -0
  170. package/dist/stream/stream_channel.cjs.map +1 -1
  171. package/dist/stream/stream_channel.d.cts +4 -2
  172. package/dist/stream/stream_channel.d.ts +4 -2
  173. package/dist/stream/stream_channel.d.ts.map +1 -1
  174. package/dist/stream/stream_channel.js +31 -0
  175. package/dist/stream/stream_channel.js.map +1 -1
  176. package/dist/stt/stt.cjs +34 -2
  177. package/dist/stt/stt.cjs.map +1 -1
  178. package/dist/stt/stt.d.cts +22 -0
  179. package/dist/stt/stt.d.ts +22 -0
  180. package/dist/stt/stt.d.ts.map +1 -1
  181. package/dist/stt/stt.js +34 -2
  182. package/dist/stt/stt.js.map +1 -1
  183. package/dist/telemetry/otel_http_exporter.cjs +24 -5
  184. package/dist/telemetry/otel_http_exporter.cjs.map +1 -1
  185. package/dist/telemetry/otel_http_exporter.d.cts +1 -0
  186. package/dist/telemetry/otel_http_exporter.d.ts +1 -0
  187. package/dist/telemetry/otel_http_exporter.d.ts.map +1 -1
  188. package/dist/telemetry/otel_http_exporter.js +24 -5
  189. package/dist/telemetry/otel_http_exporter.js.map +1 -1
  190. package/dist/telemetry/trace_types.cjs +5 -5
  191. package/dist/telemetry/trace_types.cjs.map +1 -1
  192. package/dist/telemetry/trace_types.d.cts +9 -5
  193. package/dist/telemetry/trace_types.d.ts +9 -5
  194. package/dist/telemetry/trace_types.d.ts.map +1 -1
  195. package/dist/telemetry/trace_types.js +5 -5
  196. package/dist/telemetry/trace_types.js.map +1 -1
  197. package/dist/telemetry/traces.cjs +47 -8
  198. package/dist/telemetry/traces.cjs.map +1 -1
  199. package/dist/telemetry/traces.d.ts.map +1 -1
  200. package/dist/telemetry/traces.js +47 -8
  201. package/dist/telemetry/traces.js.map +1 -1
  202. package/dist/tts/tts.cjs +64 -2
  203. package/dist/tts/tts.cjs.map +1 -1
  204. package/dist/tts/tts.d.cts +34 -0
  205. package/dist/tts/tts.d.ts +34 -0
  206. package/dist/tts/tts.d.ts.map +1 -1
  207. package/dist/tts/tts.js +64 -2
  208. package/dist/tts/tts.js.map +1 -1
  209. package/dist/version.cjs +1 -1
  210. package/dist/version.js +1 -1
  211. package/dist/voice/agent.cjs +25 -4
  212. package/dist/voice/agent.cjs.map +1 -1
  213. package/dist/voice/agent.d.cts +10 -2
  214. package/dist/voice/agent.d.ts +10 -2
  215. package/dist/voice/agent.d.ts.map +1 -1
  216. package/dist/voice/agent.js +25 -4
  217. package/dist/voice/agent.js.map +1 -1
  218. package/dist/voice/agent_activity.cjs +261 -36
  219. package/dist/voice/agent_activity.cjs.map +1 -1
  220. package/dist/voice/agent_activity.d.cts +20 -6
  221. package/dist/voice/agent_activity.d.ts +20 -6
  222. package/dist/voice/agent_activity.d.ts.map +1 -1
  223. package/dist/voice/agent_activity.js +262 -37
  224. package/dist/voice/agent_activity.js.map +1 -1
  225. package/dist/voice/agent_session.cjs +105 -48
  226. package/dist/voice/agent_session.cjs.map +1 -1
  227. package/dist/voice/agent_session.d.cts +90 -20
  228. package/dist/voice/agent_session.d.ts +90 -20
  229. package/dist/voice/agent_session.d.ts.map +1 -1
  230. package/dist/voice/agent_session.js +105 -46
  231. package/dist/voice/agent_session.js.map +1 -1
  232. package/dist/voice/audio_recognition.cjs +287 -6
  233. package/dist/voice/audio_recognition.cjs.map +1 -1
  234. package/dist/voice/audio_recognition.d.cts +42 -3
  235. package/dist/voice/audio_recognition.d.ts +42 -3
  236. package/dist/voice/audio_recognition.d.ts.map +1 -1
  237. package/dist/voice/audio_recognition.js +289 -7
  238. package/dist/voice/audio_recognition.js.map +1 -1
  239. package/dist/voice/client_events.cjs +554 -0
  240. package/dist/voice/client_events.cjs.map +1 -0
  241. package/dist/voice/client_events.d.cts +195 -0
  242. package/dist/voice/client_events.d.ts +195 -0
  243. package/dist/voice/client_events.d.ts.map +1 -0
  244. package/dist/voice/client_events.js +548 -0
  245. package/dist/voice/client_events.js.map +1 -0
  246. package/dist/voice/events.cjs +1 -0
  247. package/dist/voice/events.cjs.map +1 -1
  248. package/dist/voice/events.d.cts +8 -5
  249. package/dist/voice/events.d.ts +8 -5
  250. package/dist/voice/events.d.ts.map +1 -1
  251. package/dist/voice/events.js +1 -0
  252. package/dist/voice/events.js.map +1 -1
  253. package/dist/voice/generation.cjs +43 -8
  254. package/dist/voice/generation.cjs.map +1 -1
  255. package/dist/voice/generation.d.cts +3 -3
  256. package/dist/voice/generation.d.ts +3 -3
  257. package/dist/voice/generation.d.ts.map +1 -1
  258. package/dist/voice/generation.js +43 -8
  259. package/dist/voice/generation.js.map +1 -1
  260. package/dist/voice/index.cjs +1 -0
  261. package/dist/voice/index.cjs.map +1 -1
  262. package/dist/voice/index.d.cts +1 -0
  263. package/dist/voice/index.d.ts +1 -0
  264. package/dist/voice/index.d.ts.map +1 -1
  265. package/dist/voice/index.js +1 -0
  266. package/dist/voice/index.js.map +1 -1
  267. package/dist/voice/report.cjs +20 -8
  268. package/dist/voice/report.cjs.map +1 -1
  269. package/dist/voice/report.d.cts +5 -0
  270. package/dist/voice/report.d.ts +5 -0
  271. package/dist/voice/report.d.ts.map +1 -1
  272. package/dist/voice/report.js +20 -8
  273. package/dist/voice/report.js.map +1 -1
  274. package/dist/voice/report.test.cjs +106 -0
  275. package/dist/voice/report.test.cjs.map +1 -0
  276. package/dist/voice/report.test.js +105 -0
  277. package/dist/voice/report.test.js.map +1 -0
  278. package/dist/voice/room_io/room_io.cjs +5 -39
  279. package/dist/voice/room_io/room_io.cjs.map +1 -1
  280. package/dist/voice/room_io/room_io.d.cts +4 -9
  281. package/dist/voice/room_io/room_io.d.ts +4 -9
  282. package/dist/voice/room_io/room_io.d.ts.map +1 -1
  283. package/dist/voice/room_io/room_io.js +5 -40
  284. package/dist/voice/room_io/room_io.js.map +1 -1
  285. package/dist/voice/turn_config/endpointing.cjs +33 -0
  286. package/dist/voice/turn_config/endpointing.cjs.map +1 -0
  287. package/dist/voice/turn_config/endpointing.d.cts +30 -0
  288. package/dist/voice/turn_config/endpointing.d.ts +30 -0
  289. package/dist/voice/turn_config/endpointing.d.ts.map +1 -0
  290. package/dist/voice/turn_config/endpointing.js +9 -0
  291. package/dist/voice/turn_config/endpointing.js.map +1 -0
  292. package/dist/voice/turn_config/interruption.cjs +37 -0
  293. package/dist/voice/turn_config/interruption.cjs.map +1 -0
  294. package/dist/voice/turn_config/interruption.d.cts +53 -0
  295. package/dist/voice/turn_config/interruption.d.ts +53 -0
  296. package/dist/voice/turn_config/interruption.d.ts.map +1 -0
  297. package/dist/voice/turn_config/interruption.js +13 -0
  298. package/dist/voice/turn_config/interruption.js.map +1 -0
  299. package/dist/voice/turn_config/turn_handling.cjs +35 -0
  300. package/dist/voice/turn_config/turn_handling.cjs.map +1 -0
  301. package/dist/voice/turn_config/turn_handling.d.cts +36 -0
  302. package/dist/voice/turn_config/turn_handling.d.ts +36 -0
  303. package/dist/voice/turn_config/turn_handling.d.ts.map +1 -0
  304. package/dist/voice/turn_config/turn_handling.js +11 -0
  305. package/dist/voice/turn_config/turn_handling.js.map +1 -0
  306. package/dist/voice/turn_config/utils.cjs +97 -0
  307. package/dist/voice/turn_config/utils.cjs.map +1 -0
  308. package/dist/voice/turn_config/utils.d.cts +25 -0
  309. package/dist/voice/turn_config/utils.d.ts +25 -0
  310. package/dist/voice/turn_config/utils.d.ts.map +1 -0
  311. package/dist/voice/turn_config/utils.js +73 -0
  312. package/dist/voice/turn_config/utils.js.map +1 -0
  313. package/dist/voice/turn_config/utils.test.cjs +86 -0
  314. package/dist/voice/turn_config/utils.test.cjs.map +1 -0
  315. package/dist/voice/turn_config/utils.test.js +85 -0
  316. package/dist/voice/turn_config/utils.test.js.map +1 -0
  317. package/dist/voice/wire_format.cjs +798 -0
  318. package/dist/voice/wire_format.cjs.map +1 -0
  319. package/dist/voice/wire_format.d.cts +5503 -0
  320. package/dist/voice/wire_format.d.ts +5503 -0
  321. package/dist/voice/wire_format.d.ts.map +1 -0
  322. package/dist/voice/wire_format.js +728 -0
  323. package/dist/voice/wire_format.js.map +1 -0
  324. package/package.json +2 -1
  325. package/src/constants.ts +13 -0
  326. package/src/inference/interruption/defaults.ts +51 -0
  327. package/src/inference/interruption/errors.ts +25 -0
  328. package/src/inference/interruption/http_transport.ts +187 -0
  329. package/src/inference/interruption/interruption_cache_entry.ts +50 -0
  330. package/src/inference/interruption/interruption_detector.ts +188 -0
  331. package/src/inference/interruption/interruption_stream.ts +467 -0
  332. package/src/inference/interruption/types.ts +84 -0
  333. package/src/inference/interruption/utils.test.ts +132 -0
  334. package/src/inference/interruption/utils.ts +137 -0
  335. package/src/inference/interruption/ws_transport.ts +402 -0
  336. package/src/inference/llm.ts +9 -12
  337. package/src/inference/stt.ts +10 -3
  338. package/src/inference/tts.ts +10 -3
  339. package/src/inference/utils.ts +29 -1
  340. package/src/llm/chat_context.ts +40 -2
  341. package/src/llm/index.ts +1 -0
  342. package/src/llm/llm.ts +16 -0
  343. package/src/llm/realtime.ts +4 -0
  344. package/src/metrics/base.ts +48 -1
  345. package/src/metrics/index.ts +11 -0
  346. package/src/metrics/model_usage.test.ts +545 -0
  347. package/src/metrics/model_usage.ts +262 -0
  348. package/src/metrics/usage_collector.ts +11 -0
  349. package/src/metrics/utils.ts +11 -0
  350. package/src/stream/multi_input_stream.test.ts +6 -1
  351. package/src/stream/stream_channel.ts +34 -2
  352. package/src/stt/stt.ts +38 -0
  353. package/src/telemetry/otel_http_exporter.ts +28 -5
  354. package/src/telemetry/trace_types.ts +11 -8
  355. package/src/telemetry/traces.ts +111 -54
  356. package/src/tts/tts.ts +69 -1
  357. package/src/voice/agent.ts +30 -3
  358. package/src/voice/agent_activity.ts +327 -28
  359. package/src/voice/agent_session.ts +207 -59
  360. package/src/voice/audio_recognition.ts +385 -9
  361. package/src/voice/client_events.ts +838 -0
  362. package/src/voice/events.ts +14 -4
  363. package/src/voice/generation.ts +52 -9
  364. package/src/voice/index.ts +1 -0
  365. package/src/voice/report.test.ts +117 -0
  366. package/src/voice/report.ts +29 -6
  367. package/src/voice/room_io/room_io.ts +7 -61
  368. package/src/voice/turn_config/endpointing.ts +33 -0
  369. package/src/voice/turn_config/interruption.ts +56 -0
  370. package/src/voice/turn_config/turn_handling.ts +45 -0
  371. package/src/voice/turn_config/utils.test.ts +100 -0
  372. package/src/voice/turn_config/utils.ts +103 -0
  373. package/src/voice/wire_format.ts +827 -0
@@ -0,0 +1,181 @@
1
+ "use strict";
2
+ var __create = Object.create;
3
+ var __defProp = Object.defineProperty;
4
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
5
+ var __getOwnPropNames = Object.getOwnPropertyNames;
6
+ var __getProtoOf = Object.getPrototypeOf;
7
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
8
+ var __export = (target, all) => {
9
+ for (var name in all)
10
+ __defProp(target, name, { get: all[name], enumerable: true });
11
+ };
12
+ var __copyProps = (to, from, except, desc) => {
13
+ if (from && typeof from === "object" || typeof from === "function") {
14
+ for (let key of __getOwnPropNames(from))
15
+ if (!__hasOwnProp.call(to, key) && key !== except)
16
+ __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
17
+ }
18
+ return to;
19
+ };
20
+ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
21
+ // If the importer is in node compatibility mode or this is not an ESM
22
+ // file that has been converted to a CommonJS file using a Babel-
23
+ // compatible transform (i.e. "__esModule" has not been set), then set
24
+ // "default" to the CommonJS "module.exports" for node compatibility.
25
+ isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
26
+ mod
27
+ ));
28
+ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
29
+ var interruption_detector_exports = {};
30
+ __export(interruption_detector_exports, {
31
+ AdaptiveInterruptionDetector: () => AdaptiveInterruptionDetector
32
+ });
33
+ module.exports = __toCommonJS(interruption_detector_exports);
34
+ var import_events = __toESM(require("events"), 1);
35
+ var import_log = require("../../log.cjs");
36
+ var import_utils = require("../utils.cjs");
37
+ var import_defaults = require("./defaults.cjs");
38
+ var import_interruption_stream = require("./interruption_stream.cjs");
39
+ class AdaptiveInterruptionDetector extends import_events.default {
40
+ options;
41
+ _label;
42
+ logger = (0, import_log.log)();
43
+ // Use Set instead of WeakSet to allow iteration for propagating option updates
44
+ streams = /* @__PURE__ */ new Set();
45
+ constructor(options = {}) {
46
+ super();
47
+ const {
48
+ maxAudioDurationInS,
49
+ baseUrl,
50
+ apiKey,
51
+ apiSecret,
52
+ audioPrefixDurationInS,
53
+ threshold,
54
+ detectionIntervalInS,
55
+ inferenceTimeout,
56
+ minInterruptionDurationInS
57
+ } = { ...import_defaults.interruptionOptionDefaults, ...options };
58
+ if (maxAudioDurationInS > 3) {
59
+ throw new RangeError("maxAudioDurationInS must be less than or equal to 3.0 seconds");
60
+ }
61
+ const lkBaseUrl = baseUrl ?? process.env.LIVEKIT_REMOTE_EOT_URL ?? (0, import_utils.getDefaultInferenceUrl)();
62
+ let lkApiKey = apiKey ?? "";
63
+ let lkApiSecret = apiSecret ?? "";
64
+ let useProxy;
65
+ const isInferenceUrl = lkBaseUrl === import_utils.DEFAULT_INFERENCE_URL || lkBaseUrl === import_utils.STAGING_INFERENCE_URL;
66
+ if (isInferenceUrl) {
67
+ lkApiKey = apiKey ?? process.env.LIVEKIT_INFERENCE_API_KEY ?? process.env.LIVEKIT_API_KEY ?? "";
68
+ if (!lkApiKey) {
69
+ throw new TypeError(
70
+ "apiKey is required, either as argument or set LIVEKIT_API_KEY environmental variable"
71
+ );
72
+ }
73
+ lkApiSecret = apiSecret ?? process.env.LIVEKIT_INFERENCE_API_SECRET ?? process.env.LIVEKIT_API_SECRET ?? "";
74
+ if (!lkApiSecret) {
75
+ throw new TypeError(
76
+ "apiSecret is required, either as argument or set LIVEKIT_API_SECRET environmental variable"
77
+ );
78
+ }
79
+ useProxy = true;
80
+ } else {
81
+ useProxy = false;
82
+ }
83
+ this.options = {
84
+ sampleRate: import_defaults.SAMPLE_RATE,
85
+ threshold,
86
+ minFrames: Math.ceil(minInterruptionDurationInS * import_defaults.FRAMES_PER_SECOND),
87
+ maxAudioDurationInS,
88
+ audioPrefixDurationInS,
89
+ detectionIntervalInS,
90
+ inferenceTimeout,
91
+ baseUrl: lkBaseUrl,
92
+ apiKey: lkApiKey,
93
+ apiSecret: lkApiSecret,
94
+ useProxy,
95
+ minInterruptionDurationInS
96
+ };
97
+ this._label = `${this.constructor.name}`;
98
+ this.logger.debug(
99
+ {
100
+ baseUrl: this.options.baseUrl,
101
+ detectionIntervalInS: this.options.detectionIntervalInS,
102
+ audioPrefixDurationInS: this.options.audioPrefixDurationInS,
103
+ maxAudioDurationInS: this.options.maxAudioDurationInS,
104
+ minFrames: this.options.minFrames,
105
+ threshold: this.options.threshold,
106
+ inferenceTimeout: this.options.inferenceTimeout,
107
+ useProxy: this.options.useProxy
108
+ },
109
+ "adaptive interruption detector initialized"
110
+ );
111
+ }
112
+ /**
113
+ * The model identifier for this detector.
114
+ */
115
+ get model() {
116
+ return "adaptive interruption";
117
+ }
118
+ /**
119
+ * The provider identifier for this detector.
120
+ */
121
+ get provider() {
122
+ return "livekit";
123
+ }
124
+ /**
125
+ * The label for this detector instance.
126
+ */
127
+ get label() {
128
+ return this._label;
129
+ }
130
+ /**
131
+ * The sample rate used for audio processing.
132
+ */
133
+ get sampleRate() {
134
+ return this.options.sampleRate;
135
+ }
136
+ /**
137
+ * Emit an error event from the detector.
138
+ */
139
+ emitError(error) {
140
+ this.emit("error", error);
141
+ }
142
+ /**
143
+ * Creates a new InterruptionStreamBase for internal use.
144
+ * The stream can receive audio frames and sentinels via pushFrame().
145
+ * Use this when you need direct access to the stream for pushing frames.
146
+ */
147
+ createStream() {
148
+ const streamBase = new import_interruption_stream.InterruptionStreamBase(this, {});
149
+ this.streams.add(streamBase);
150
+ return streamBase;
151
+ }
152
+ /**
153
+ * Remove a stream from tracking (called when stream is closed).
154
+ */
155
+ removeStream(stream) {
156
+ this.streams.delete(stream);
157
+ }
158
+ /**
159
+ * Update options for the detector and propagate to all active streams.
160
+ * For WebSocket streams, this triggers a reconnection with new settings.
161
+ */
162
+ async updateOptions(options) {
163
+ if (options.threshold !== void 0) {
164
+ this.options.threshold = options.threshold;
165
+ }
166
+ if (options.minInterruptionDurationInS !== void 0) {
167
+ this.options.minInterruptionDurationInS = options.minInterruptionDurationInS;
168
+ this.options.minFrames = Math.ceil(options.minInterruptionDurationInS * import_defaults.FRAMES_PER_SECOND);
169
+ }
170
+ const updatePromises = [];
171
+ for (const stream of this.streams) {
172
+ updatePromises.push(stream.updateOptions(options));
173
+ }
174
+ await Promise.all(updatePromises);
175
+ }
176
+ }
177
+ // Annotate the CommonJS export names for ESM import in node:
178
+ 0 && (module.exports = {
179
+ AdaptiveInterruptionDetector
180
+ });
181
+ //# sourceMappingURL=interruption_detector.cjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../../../src/inference/interruption/interruption_detector.ts"],"sourcesContent":["// SPDX-FileCopyrightText: 2026 LiveKit, Inc.\n//\n// SPDX-License-Identifier: Apache-2.0\nimport type { TypedEventEmitter } from '@livekit/typed-emitter';\nimport EventEmitter from 'events';\nimport { log } from '../../log.js';\nimport type { InterruptionMetrics } from '../../metrics/base.js';\nimport { DEFAULT_INFERENCE_URL, STAGING_INFERENCE_URL, getDefaultInferenceUrl } from '../utils.js';\nimport { FRAMES_PER_SECOND, SAMPLE_RATE, interruptionOptionDefaults } from './defaults.js';\nimport type { InterruptionDetectionError } from './errors.js';\nimport { InterruptionStreamBase } from './interruption_stream.js';\nimport type { InterruptionOptions, OverlappingSpeechEvent } from './types.js';\n\ntype InterruptionCallbacks = {\n user_overlapping_speech: (event: OverlappingSpeechEvent) => void;\n metrics_collected: (metrics: InterruptionMetrics) => void;\n error: (error: InterruptionDetectionError) => void;\n};\n\nexport type AdaptiveInterruptionDetectorOptions = Omit<Partial<InterruptionOptions>, 'useProxy'>;\n\nexport class AdaptiveInterruptionDetector extends (EventEmitter as new () => TypedEventEmitter<InterruptionCallbacks>) {\n options: InterruptionOptions;\n private readonly _label: string;\n private logger = log();\n // Use Set instead of WeakSet to allow iteration for propagating option updates\n private streams: Set<InterruptionStreamBase> = new Set();\n\n constructor(options: AdaptiveInterruptionDetectorOptions = {}) {\n super();\n\n const {\n maxAudioDurationInS,\n baseUrl,\n apiKey,\n apiSecret,\n audioPrefixDurationInS,\n threshold,\n detectionIntervalInS,\n inferenceTimeout,\n minInterruptionDurationInS,\n } = { ...interruptionOptionDefaults, ...options };\n\n if (maxAudioDurationInS > 3.0) {\n throw new RangeError('maxAudioDurationInS must be less than or equal to 3.0 seconds');\n }\n\n const lkBaseUrl = baseUrl ?? process.env.LIVEKIT_REMOTE_EOT_URL ?? getDefaultInferenceUrl();\n let lkApiKey = apiKey ?? '';\n let lkApiSecret = apiSecret ?? '';\n let useProxy: boolean;\n\n // Use LiveKit credentials if using the inference service (production or staging)\n const isInferenceUrl =\n lkBaseUrl === DEFAULT_INFERENCE_URL || lkBaseUrl === STAGING_INFERENCE_URL;\n if (isInferenceUrl) {\n lkApiKey =\n apiKey ?? process.env.LIVEKIT_INFERENCE_API_KEY ?? process.env.LIVEKIT_API_KEY ?? '';\n if (!lkApiKey) {\n throw new TypeError(\n 'apiKey is required, either as argument or set LIVEKIT_API_KEY environmental variable',\n );\n }\n\n lkApiSecret =\n apiSecret ??\n process.env.LIVEKIT_INFERENCE_API_SECRET ??\n process.env.LIVEKIT_API_SECRET ??\n '';\n if (!lkApiSecret) {\n throw new TypeError(\n 'apiSecret is required, either as argument or set LIVEKIT_API_SECRET environmental variable',\n );\n }\n useProxy = true;\n } else {\n useProxy = false;\n }\n\n this.options = {\n sampleRate: SAMPLE_RATE,\n threshold,\n minFrames: Math.ceil(minInterruptionDurationInS * FRAMES_PER_SECOND),\n maxAudioDurationInS,\n audioPrefixDurationInS,\n detectionIntervalInS,\n inferenceTimeout,\n baseUrl: lkBaseUrl,\n apiKey: lkApiKey,\n apiSecret: lkApiSecret,\n useProxy,\n minInterruptionDurationInS,\n };\n\n this._label = `${this.constructor.name}`;\n\n this.logger.debug(\n {\n baseUrl: this.options.baseUrl,\n detectionIntervalInS: this.options.detectionIntervalInS,\n audioPrefixDurationInS: this.options.audioPrefixDurationInS,\n maxAudioDurationInS: this.options.maxAudioDurationInS,\n minFrames: this.options.minFrames,\n threshold: this.options.threshold,\n inferenceTimeout: this.options.inferenceTimeout,\n useProxy: this.options.useProxy,\n },\n 'adaptive interruption detector initialized',\n );\n }\n\n /**\n * The model identifier for this detector.\n */\n get model(): string {\n return 'adaptive interruption';\n }\n\n /**\n * The provider identifier for this detector.\n */\n get provider(): string {\n return 'livekit';\n }\n\n /**\n * The label for this detector instance.\n */\n get label(): string {\n return this._label;\n }\n\n /**\n * The sample rate used for audio processing.\n */\n get sampleRate(): number {\n return this.options.sampleRate;\n }\n\n /**\n * Emit an error event from the detector.\n */\n emitError(error: InterruptionDetectionError): void {\n this.emit('error', error);\n }\n\n /**\n * Creates a new InterruptionStreamBase for internal use.\n * The stream can receive audio frames and sentinels via pushFrame().\n * Use this when you need direct access to the stream for pushing frames.\n */\n createStream(): InterruptionStreamBase {\n const streamBase = new InterruptionStreamBase(this, {});\n this.streams.add(streamBase);\n return streamBase;\n }\n\n /**\n * Remove a stream from tracking (called when stream is closed).\n */\n removeStream(stream: InterruptionStreamBase): void {\n this.streams.delete(stream);\n }\n\n /**\n * Update options for the detector and propagate to all active streams.\n * For WebSocket streams, this triggers a reconnection with new settings.\n */\n async updateOptions(options: {\n threshold?: number;\n minInterruptionDurationInS?: number;\n }): Promise<void> {\n if (options.threshold !== undefined) {\n this.options.threshold = options.threshold;\n }\n if (options.minInterruptionDurationInS !== undefined) {\n this.options.minInterruptionDurationInS = options.minInterruptionDurationInS;\n this.options.minFrames = Math.ceil(options.minInterruptionDurationInS * FRAMES_PER_SECOND);\n }\n\n // Propagate option updates to all active streams (matching Python behavior)\n const updatePromises: Promise<void>[] = [];\n for (const stream of this.streams) {\n updatePromises.push(stream.updateOptions(options));\n }\n await Promise.all(updatePromises);\n }\n}\n"],"mappings":"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","names":["EventEmitter"]}
@@ -0,0 +1,59 @@
1
+ import type { TypedEventEmitter } from '@livekit/typed-emitter';
2
+ import type { InterruptionMetrics } from '../../metrics/base.js';
3
+ import type { InterruptionDetectionError } from './errors.js';
4
+ import { InterruptionStreamBase } from './interruption_stream.js';
5
+ import type { InterruptionOptions, OverlappingSpeechEvent } from './types.js';
6
+ type InterruptionCallbacks = {
7
+ user_overlapping_speech: (event: OverlappingSpeechEvent) => void;
8
+ metrics_collected: (metrics: InterruptionMetrics) => void;
9
+ error: (error: InterruptionDetectionError) => void;
10
+ };
11
+ export type AdaptiveInterruptionDetectorOptions = Omit<Partial<InterruptionOptions>, 'useProxy'>;
12
+ declare const AdaptiveInterruptionDetector_base: new () => TypedEventEmitter<InterruptionCallbacks>;
13
+ export declare class AdaptiveInterruptionDetector extends AdaptiveInterruptionDetector_base {
14
+ options: InterruptionOptions;
15
+ private readonly _label;
16
+ private logger;
17
+ private streams;
18
+ constructor(options?: AdaptiveInterruptionDetectorOptions);
19
+ /**
20
+ * The model identifier for this detector.
21
+ */
22
+ get model(): string;
23
+ /**
24
+ * The provider identifier for this detector.
25
+ */
26
+ get provider(): string;
27
+ /**
28
+ * The label for this detector instance.
29
+ */
30
+ get label(): string;
31
+ /**
32
+ * The sample rate used for audio processing.
33
+ */
34
+ get sampleRate(): number;
35
+ /**
36
+ * Emit an error event from the detector.
37
+ */
38
+ emitError(error: InterruptionDetectionError): void;
39
+ /**
40
+ * Creates a new InterruptionStreamBase for internal use.
41
+ * The stream can receive audio frames and sentinels via pushFrame().
42
+ * Use this when you need direct access to the stream for pushing frames.
43
+ */
44
+ createStream(): InterruptionStreamBase;
45
+ /**
46
+ * Remove a stream from tracking (called when stream is closed).
47
+ */
48
+ removeStream(stream: InterruptionStreamBase): void;
49
+ /**
50
+ * Update options for the detector and propagate to all active streams.
51
+ * For WebSocket streams, this triggers a reconnection with new settings.
52
+ */
53
+ updateOptions(options: {
54
+ threshold?: number;
55
+ minInterruptionDurationInS?: number;
56
+ }): Promise<void>;
57
+ }
58
+ export {};
59
+ //# sourceMappingURL=interruption_detector.d.ts.map
@@ -0,0 +1,59 @@
1
+ import type { TypedEventEmitter } from '@livekit/typed-emitter';
2
+ import type { InterruptionMetrics } from '../../metrics/base.js';
3
+ import type { InterruptionDetectionError } from './errors.js';
4
+ import { InterruptionStreamBase } from './interruption_stream.js';
5
+ import type { InterruptionOptions, OverlappingSpeechEvent } from './types.js';
6
+ type InterruptionCallbacks = {
7
+ user_overlapping_speech: (event: OverlappingSpeechEvent) => void;
8
+ metrics_collected: (metrics: InterruptionMetrics) => void;
9
+ error: (error: InterruptionDetectionError) => void;
10
+ };
11
+ export type AdaptiveInterruptionDetectorOptions = Omit<Partial<InterruptionOptions>, 'useProxy'>;
12
+ declare const AdaptiveInterruptionDetector_base: new () => TypedEventEmitter<InterruptionCallbacks>;
13
+ export declare class AdaptiveInterruptionDetector extends AdaptiveInterruptionDetector_base {
14
+ options: InterruptionOptions;
15
+ private readonly _label;
16
+ private logger;
17
+ private streams;
18
+ constructor(options?: AdaptiveInterruptionDetectorOptions);
19
+ /**
20
+ * The model identifier for this detector.
21
+ */
22
+ get model(): string;
23
+ /**
24
+ * The provider identifier for this detector.
25
+ */
26
+ get provider(): string;
27
+ /**
28
+ * The label for this detector instance.
29
+ */
30
+ get label(): string;
31
+ /**
32
+ * The sample rate used for audio processing.
33
+ */
34
+ get sampleRate(): number;
35
+ /**
36
+ * Emit an error event from the detector.
37
+ */
38
+ emitError(error: InterruptionDetectionError): void;
39
+ /**
40
+ * Creates a new InterruptionStreamBase for internal use.
41
+ * The stream can receive audio frames and sentinels via pushFrame().
42
+ * Use this when you need direct access to the stream for pushing frames.
43
+ */
44
+ createStream(): InterruptionStreamBase;
45
+ /**
46
+ * Remove a stream from tracking (called when stream is closed).
47
+ */
48
+ removeStream(stream: InterruptionStreamBase): void;
49
+ /**
50
+ * Update options for the detector and propagate to all active streams.
51
+ * For WebSocket streams, this triggers a reconnection with new settings.
52
+ */
53
+ updateOptions(options: {
54
+ threshold?: number;
55
+ minInterruptionDurationInS?: number;
56
+ }): Promise<void>;
57
+ }
58
+ export {};
59
+ //# sourceMappingURL=interruption_detector.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"interruption_detector.d.ts","sourceRoot":"","sources":["../../../src/inference/interruption/interruption_detector.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,wBAAwB,CAAC;AAGhE,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,uBAAuB,CAAC;AAGjE,OAAO,KAAK,EAAE,0BAA0B,EAAE,MAAM,aAAa,CAAC;AAC9D,OAAO,EAAE,sBAAsB,EAAE,MAAM,0BAA0B,CAAC;AAClE,OAAO,KAAK,EAAE,mBAAmB,EAAE,sBAAsB,EAAE,MAAM,YAAY,CAAC;AAE9E,KAAK,qBAAqB,GAAG;IAC3B,uBAAuB,EAAE,CAAC,KAAK,EAAE,sBAAsB,KAAK,IAAI,CAAC;IACjE,iBAAiB,EAAE,CAAC,OAAO,EAAE,mBAAmB,KAAK,IAAI,CAAC;IAC1D,KAAK,EAAE,CAAC,KAAK,EAAE,0BAA0B,KAAK,IAAI,CAAC;CACpD,CAAC;AAEF,MAAM,MAAM,mCAAmC,GAAG,IAAI,CAAC,OAAO,CAAC,mBAAmB,CAAC,EAAE,UAAU,CAAC,CAAC;2DAEpB,kBAAkB,qBAAqB,CAAC;AAArH,qBAAa,4BAA6B,SAAQ,iCAAoE;IACpH,OAAO,EAAE,mBAAmB,CAAC;IAC7B,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAS;IAChC,OAAO,CAAC,MAAM,CAAS;IAEvB,OAAO,CAAC,OAAO,CAA0C;gBAE7C,OAAO,GAAE,mCAAwC;IAmF7D;;OAEG;IACH,IAAI,KAAK,IAAI,MAAM,CAElB;IAED;;OAEG;IACH,IAAI,QAAQ,IAAI,MAAM,CAErB;IAED;;OAEG;IACH,IAAI,KAAK,IAAI,MAAM,CAElB;IAED;;OAEG;IACH,IAAI,UAAU,IAAI,MAAM,CAEvB;IAED;;OAEG;IACH,SAAS,CAAC,KAAK,EAAE,0BAA0B,GAAG,IAAI;IAIlD;;;;OAIG;IACH,YAAY,IAAI,sBAAsB;IAMtC;;OAEG;IACH,YAAY,CAAC,MAAM,EAAE,sBAAsB,GAAG,IAAI;IAIlD;;;OAGG;IACG,aAAa,CAAC,OAAO,EAAE;QAC3B,SAAS,CAAC,EAAE,MAAM,CAAC;QACnB,0BAA0B,CAAC,EAAE,MAAM,CAAC;KACrC,GAAG,OAAO,CAAC,IAAI,CAAC;CAgBlB"}
@@ -0,0 +1,147 @@
1
+ import EventEmitter from "events";
2
+ import { log } from "../../log.js";
3
+ import { DEFAULT_INFERENCE_URL, STAGING_INFERENCE_URL, getDefaultInferenceUrl } from "../utils.js";
4
+ import { FRAMES_PER_SECOND, SAMPLE_RATE, interruptionOptionDefaults } from "./defaults.js";
5
+ import { InterruptionStreamBase } from "./interruption_stream.js";
6
+ class AdaptiveInterruptionDetector extends EventEmitter {
7
+ options;
8
+ _label;
9
+ logger = log();
10
+ // Use Set instead of WeakSet to allow iteration for propagating option updates
11
+ streams = /* @__PURE__ */ new Set();
12
+ constructor(options = {}) {
13
+ super();
14
+ const {
15
+ maxAudioDurationInS,
16
+ baseUrl,
17
+ apiKey,
18
+ apiSecret,
19
+ audioPrefixDurationInS,
20
+ threshold,
21
+ detectionIntervalInS,
22
+ inferenceTimeout,
23
+ minInterruptionDurationInS
24
+ } = { ...interruptionOptionDefaults, ...options };
25
+ if (maxAudioDurationInS > 3) {
26
+ throw new RangeError("maxAudioDurationInS must be less than or equal to 3.0 seconds");
27
+ }
28
+ const lkBaseUrl = baseUrl ?? process.env.LIVEKIT_REMOTE_EOT_URL ?? getDefaultInferenceUrl();
29
+ let lkApiKey = apiKey ?? "";
30
+ let lkApiSecret = apiSecret ?? "";
31
+ let useProxy;
32
+ const isInferenceUrl = lkBaseUrl === DEFAULT_INFERENCE_URL || lkBaseUrl === STAGING_INFERENCE_URL;
33
+ if (isInferenceUrl) {
34
+ lkApiKey = apiKey ?? process.env.LIVEKIT_INFERENCE_API_KEY ?? process.env.LIVEKIT_API_KEY ?? "";
35
+ if (!lkApiKey) {
36
+ throw new TypeError(
37
+ "apiKey is required, either as argument or set LIVEKIT_API_KEY environmental variable"
38
+ );
39
+ }
40
+ lkApiSecret = apiSecret ?? process.env.LIVEKIT_INFERENCE_API_SECRET ?? process.env.LIVEKIT_API_SECRET ?? "";
41
+ if (!lkApiSecret) {
42
+ throw new TypeError(
43
+ "apiSecret is required, either as argument or set LIVEKIT_API_SECRET environmental variable"
44
+ );
45
+ }
46
+ useProxy = true;
47
+ } else {
48
+ useProxy = false;
49
+ }
50
+ this.options = {
51
+ sampleRate: SAMPLE_RATE,
52
+ threshold,
53
+ minFrames: Math.ceil(minInterruptionDurationInS * FRAMES_PER_SECOND),
54
+ maxAudioDurationInS,
55
+ audioPrefixDurationInS,
56
+ detectionIntervalInS,
57
+ inferenceTimeout,
58
+ baseUrl: lkBaseUrl,
59
+ apiKey: lkApiKey,
60
+ apiSecret: lkApiSecret,
61
+ useProxy,
62
+ minInterruptionDurationInS
63
+ };
64
+ this._label = `${this.constructor.name}`;
65
+ this.logger.debug(
66
+ {
67
+ baseUrl: this.options.baseUrl,
68
+ detectionIntervalInS: this.options.detectionIntervalInS,
69
+ audioPrefixDurationInS: this.options.audioPrefixDurationInS,
70
+ maxAudioDurationInS: this.options.maxAudioDurationInS,
71
+ minFrames: this.options.minFrames,
72
+ threshold: this.options.threshold,
73
+ inferenceTimeout: this.options.inferenceTimeout,
74
+ useProxy: this.options.useProxy
75
+ },
76
+ "adaptive interruption detector initialized"
77
+ );
78
+ }
79
+ /**
80
+ * The model identifier for this detector.
81
+ */
82
+ get model() {
83
+ return "adaptive interruption";
84
+ }
85
+ /**
86
+ * The provider identifier for this detector.
87
+ */
88
+ get provider() {
89
+ return "livekit";
90
+ }
91
+ /**
92
+ * The label for this detector instance.
93
+ */
94
+ get label() {
95
+ return this._label;
96
+ }
97
+ /**
98
+ * The sample rate used for audio processing.
99
+ */
100
+ get sampleRate() {
101
+ return this.options.sampleRate;
102
+ }
103
+ /**
104
+ * Emit an error event from the detector.
105
+ */
106
+ emitError(error) {
107
+ this.emit("error", error);
108
+ }
109
+ /**
110
+ * Creates a new InterruptionStreamBase for internal use.
111
+ * The stream can receive audio frames and sentinels via pushFrame().
112
+ * Use this when you need direct access to the stream for pushing frames.
113
+ */
114
+ createStream() {
115
+ const streamBase = new InterruptionStreamBase(this, {});
116
+ this.streams.add(streamBase);
117
+ return streamBase;
118
+ }
119
+ /**
120
+ * Remove a stream from tracking (called when stream is closed).
121
+ */
122
+ removeStream(stream) {
123
+ this.streams.delete(stream);
124
+ }
125
+ /**
126
+ * Update options for the detector and propagate to all active streams.
127
+ * For WebSocket streams, this triggers a reconnection with new settings.
128
+ */
129
+ async updateOptions(options) {
130
+ if (options.threshold !== void 0) {
131
+ this.options.threshold = options.threshold;
132
+ }
133
+ if (options.minInterruptionDurationInS !== void 0) {
134
+ this.options.minInterruptionDurationInS = options.minInterruptionDurationInS;
135
+ this.options.minFrames = Math.ceil(options.minInterruptionDurationInS * FRAMES_PER_SECOND);
136
+ }
137
+ const updatePromises = [];
138
+ for (const stream of this.streams) {
139
+ updatePromises.push(stream.updateOptions(options));
140
+ }
141
+ await Promise.all(updatePromises);
142
+ }
143
+ }
144
+ export {
145
+ AdaptiveInterruptionDetector
146
+ };
147
+ //# sourceMappingURL=interruption_detector.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../../../src/inference/interruption/interruption_detector.ts"],"sourcesContent":["// SPDX-FileCopyrightText: 2026 LiveKit, Inc.\n//\n// SPDX-License-Identifier: Apache-2.0\nimport type { TypedEventEmitter } from '@livekit/typed-emitter';\nimport EventEmitter from 'events';\nimport { log } from '../../log.js';\nimport type { InterruptionMetrics } from '../../metrics/base.js';\nimport { DEFAULT_INFERENCE_URL, STAGING_INFERENCE_URL, getDefaultInferenceUrl } from '../utils.js';\nimport { FRAMES_PER_SECOND, SAMPLE_RATE, interruptionOptionDefaults } from './defaults.js';\nimport type { InterruptionDetectionError } from './errors.js';\nimport { InterruptionStreamBase } from './interruption_stream.js';\nimport type { InterruptionOptions, OverlappingSpeechEvent } from './types.js';\n\ntype InterruptionCallbacks = {\n user_overlapping_speech: (event: OverlappingSpeechEvent) => void;\n metrics_collected: (metrics: InterruptionMetrics) => void;\n error: (error: InterruptionDetectionError) => void;\n};\n\nexport type AdaptiveInterruptionDetectorOptions = Omit<Partial<InterruptionOptions>, 'useProxy'>;\n\nexport class AdaptiveInterruptionDetector extends (EventEmitter as new () => TypedEventEmitter<InterruptionCallbacks>) {\n options: InterruptionOptions;\n private readonly _label: string;\n private logger = log();\n // Use Set instead of WeakSet to allow iteration for propagating option updates\n private streams: Set<InterruptionStreamBase> = new Set();\n\n constructor(options: AdaptiveInterruptionDetectorOptions = {}) {\n super();\n\n const {\n maxAudioDurationInS,\n baseUrl,\n apiKey,\n apiSecret,\n audioPrefixDurationInS,\n threshold,\n detectionIntervalInS,\n inferenceTimeout,\n minInterruptionDurationInS,\n } = { ...interruptionOptionDefaults, ...options };\n\n if (maxAudioDurationInS > 3.0) {\n throw new RangeError('maxAudioDurationInS must be less than or equal to 3.0 seconds');\n }\n\n const lkBaseUrl = baseUrl ?? process.env.LIVEKIT_REMOTE_EOT_URL ?? getDefaultInferenceUrl();\n let lkApiKey = apiKey ?? '';\n let lkApiSecret = apiSecret ?? '';\n let useProxy: boolean;\n\n // Use LiveKit credentials if using the inference service (production or staging)\n const isInferenceUrl =\n lkBaseUrl === DEFAULT_INFERENCE_URL || lkBaseUrl === STAGING_INFERENCE_URL;\n if (isInferenceUrl) {\n lkApiKey =\n apiKey ?? process.env.LIVEKIT_INFERENCE_API_KEY ?? process.env.LIVEKIT_API_KEY ?? '';\n if (!lkApiKey) {\n throw new TypeError(\n 'apiKey is required, either as argument or set LIVEKIT_API_KEY environmental variable',\n );\n }\n\n lkApiSecret =\n apiSecret ??\n process.env.LIVEKIT_INFERENCE_API_SECRET ??\n process.env.LIVEKIT_API_SECRET ??\n '';\n if (!lkApiSecret) {\n throw new TypeError(\n 'apiSecret is required, either as argument or set LIVEKIT_API_SECRET environmental variable',\n );\n }\n useProxy = true;\n } else {\n useProxy = false;\n }\n\n this.options = {\n sampleRate: SAMPLE_RATE,\n threshold,\n minFrames: Math.ceil(minInterruptionDurationInS * FRAMES_PER_SECOND),\n maxAudioDurationInS,\n audioPrefixDurationInS,\n detectionIntervalInS,\n inferenceTimeout,\n baseUrl: lkBaseUrl,\n apiKey: lkApiKey,\n apiSecret: lkApiSecret,\n useProxy,\n minInterruptionDurationInS,\n };\n\n this._label = `${this.constructor.name}`;\n\n this.logger.debug(\n {\n baseUrl: this.options.baseUrl,\n detectionIntervalInS: this.options.detectionIntervalInS,\n audioPrefixDurationInS: this.options.audioPrefixDurationInS,\n maxAudioDurationInS: this.options.maxAudioDurationInS,\n minFrames: this.options.minFrames,\n threshold: this.options.threshold,\n inferenceTimeout: this.options.inferenceTimeout,\n useProxy: this.options.useProxy,\n },\n 'adaptive interruption detector initialized',\n );\n }\n\n /**\n * The model identifier for this detector.\n */\n get model(): string {\n return 'adaptive interruption';\n }\n\n /**\n * The provider identifier for this detector.\n */\n get provider(): string {\n return 'livekit';\n }\n\n /**\n * The label for this detector instance.\n */\n get label(): string {\n return this._label;\n }\n\n /**\n * The sample rate used for audio processing.\n */\n get sampleRate(): number {\n return this.options.sampleRate;\n }\n\n /**\n * Emit an error event from the detector.\n */\n emitError(error: InterruptionDetectionError): void {\n this.emit('error', error);\n }\n\n /**\n * Creates a new InterruptionStreamBase for internal use.\n * The stream can receive audio frames and sentinels via pushFrame().\n * Use this when you need direct access to the stream for pushing frames.\n */\n createStream(): InterruptionStreamBase {\n const streamBase = new InterruptionStreamBase(this, {});\n this.streams.add(streamBase);\n return streamBase;\n }\n\n /**\n * Remove a stream from tracking (called when stream is closed).\n */\n removeStream(stream: InterruptionStreamBase): void {\n this.streams.delete(stream);\n }\n\n /**\n * Update options for the detector and propagate to all active streams.\n * For WebSocket streams, this triggers a reconnection with new settings.\n */\n async updateOptions(options: {\n threshold?: number;\n minInterruptionDurationInS?: number;\n }): Promise<void> {\n if (options.threshold !== undefined) {\n this.options.threshold = options.threshold;\n }\n if (options.minInterruptionDurationInS !== undefined) {\n this.options.minInterruptionDurationInS = options.minInterruptionDurationInS;\n this.options.minFrames = Math.ceil(options.minInterruptionDurationInS * FRAMES_PER_SECOND);\n }\n\n // Propagate option updates to all active streams (matching Python behavior)\n const updatePromises: Promise<void>[] = [];\n for (const stream of this.streams) {\n updatePromises.push(stream.updateOptions(options));\n }\n await Promise.all(updatePromises);\n }\n}\n"],"mappings":"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","names":[]}