
    /j                       S SK Jr  S SKrS SKrS SKrS SKrS SKJr  S SKJ	r	  S SK
Jr  S SKJrJrJr  S SKJr  S SKJr  S S	KJr  S
SKJrJrJrJrJr  S
SKJrJrJrJ r   S
SK!J"r"  S
SK#J$r$  S
SKJ%r%  S
SK&J'r'J(r(  S
SK)J*r*J+r+  S
SKJ,r,J-r-  SSKJ.r.  SSK/J0r0  SSK1J2r2  SSK3J4r4  \(       a  SSK5J6r6  Sr7Sr8\ " S S5      5       r9\ " S S5      5       r: " S S \5      r; " S! S"5      r< " S# S$5      r=g)%    )annotationsN)deque)AsyncIterable)	dataclass)TYPE_CHECKINGAnyProtocol)trace)ReadableSpan)rtc   )	inferencellmsttutilsvad)_AgentSpeechEndedSentinel_AgentSpeechStartedSentinel_OverlapSpeechEndedSentinel_OverlapSpeechStartedSentinel)LanguageCodelogger)SpeechEvent)trace_typestracer)	NOT_GIVEN
NotGivenOr)aiois_given   )io)_set_participant_attributes)BaseEndpointing)TurnDetectionMode)AgentSession      c                  ^    \ rS rSr% S\S'    S\S'   S\S'   S\S	'   S\S
'   S\S'   S\S'   Srg)_EndOfTurnInfo+   bool
skip_replystrnew_transcriptfloattranscript_confidencefloat | Nonestarted_speaking_atstopped_speaking_attranscription_delayend_of_turn_delay N__name__
__module____qualname____firstlineno____annotations____static_attributes__r7       W/app/agent/.venv/lib/python3.13/site-packages/livekit/agents/voice/audio_recognition.pyr*   r*   +   s1    c   &%%%%%##r?   r*   c                  4    \ rS rSr% S\S'   S\S'   S\S'   Srg	)
_PreemptiveGenerationInfo9   r.   r/   r0   r1   r2   r3   r7   Nr8   r7   r?   r@   rB   rB   9   s      %%r?   rB   c                  v    \ rS rSrSS jrSS jrSS jrSS jrSS jrSS.SS	 jjr	SS
 jr
SS jrSS jrSrg)RecognitionHooks@   c                    g Nr7   selfevs     r@   on_interruption RecognitionHooks.on_interruptionA   s    Sr?   c                    g rH   r7   rI   s     r@   on_start_of_speech#RecognitionHooks.on_start_of_speechB   s    3r?   c                    g rH   r7   rI   s     r@   on_vad_inference_done&RecognitionHooks.on_vad_inference_doneC   s    sr?   c                    g rH   r7   rI   s     r@   on_end_of_speech!RecognitionHooks.on_end_of_speechD   s    r?   c                   g rH   r7   rJ   rK   speakings      r@   on_interim_transcript&RecognitionHooks.on_interim_transcriptE   s    \_r?   NrY   c                   g rH   r7   rX   s      r@   on_final_transcript$RecognitionHooks.on_final_transcriptF   s    adr?   c                    g rH   r7   rJ   infos     r@   on_end_of_turnRecognitionHooks.on_end_of_turnG   s    Cr?   c                    g rH   r7   ra   s     r@   on_preemptive_generation)RecognitionHooks.on_preemptive_generationH   s    QTr?   c                    g rH   r7   rJ   s    r@   retrieve_chat_ctx"RecognitionHooks.retrieve_chat_ctxI   s    Cr?   r7   rK   z inference.OverlappingSpeechEventreturnNone)rK   zvad.VADEvent | Nonerm   rn   rK   zvad.VADEventrm   rn   )rK   stt.SpeechEventrY   zbool | Nonerm   rn   )rb   r*   rm   r,   )rb   rB   rm   rn   )rm   llm.ChatContext)r9   r:   r;   r<   rL   rO   rR   rU   rZ   r^   rc   rf   rj   r>   r7   r?   r@   rE   rE   @   s     PFBD_RVd?T7r?   rE   c                      \ rS rSrSrSS jr\SS j5       r\SS j5       r\	R                  " \S9SS j5       rSS jrS	rg
)_STTPipelineL   u   Transferable STT pipeline that survives agent handoff.

The pump task iterates the STT generator and forwards events into event_ch.
It is never cancelled during handoff — only the consumer is swapped.
c                P  ^  UT l         [        R                  [        R                     " 5       T l        [        R                  [        R                     " 5       T l        [        R                  " T R                  5       5      T l        T R                  R                  U 4S j5        g )Nc                8   > TR                   R                  5       $ rH   )	_event_chclose)_rJ   s    r@   <lambda>'_STTPipeline.__init__.<locals>.<lambda>X   s    DNN4H4H4Jr?   )	_stt_noder   Chanr   
AudioFrame	_audio_chr   r   rw   asynciocreate_task	_stt_pump
_pump_taskadd_done_callback)rJ   stt_nodes   ` r@   __init___STTPipeline.__init__S   sd    !#..13#//24!--dnn.>?))*JKr?   c                    U R                   $ rH   )r   ri   s    r@   audio_ch_STTPipeline.audio_chZ       ~~r?   c                    U R                   $ rH   )rw   ri   s    r@   event_ch_STTPipeline.event_ch^   r   r?   r   c                  #    SSK Jn  U R                  U R                  U" 5       5      n[        R
                  " U5      (       a
  UI Sh  vN nUc  g[        U[        5      (       aZ  U  Sh  vN n[        U[        R                  5      (       d   S[        U5       35       eU R                  R                  U5        MX  g Nx NV
 g7f)u   Iterate the STT generator and forward events into *event_ch*.

This task owns the generator lifecycle and is never cancelled during
handoff — only the consumer is swapped.
r!   )ModelSettingsNz&STT node must yield SpeechEvent, got: )agentr   r|   r   r   iscoroutine
isinstancer   r   r   typerw   send_nowait)rJ   r   noderK   s       r@   r   _STTPipeline._stt_pumpb   s      	)~~dnnmo>t$$:D<dM**  /b!"coo66 <T"XJG6 **2. + /Ds7   AC	
CC	*C.C/C2AC	CC	c                `   #    [         R                  " U R                  5      I S h  vN   g  N7frH   )r   cancel_and_waitr   ri   s    r@   aclose_STTPipeline.aclosey   s     !!$//222s   $.,.)r   rw   r   r|   N)r   z
io.STTNoderm   rn   )rm   zaio.Chan[rtc.AudioFrame])rm   aio.Chan[stt.SpeechEvent]rm   rn   )r9   r:   r;   r<   __doc__r   propertyr   r   r   log_exceptionsr   r   r   r>   r7   r?   r@   rs   rs   L   sY    L     (/ )/,3r?   rs   c                     \ rS rSrSSS.                   S+S jjr\\\\S.         S,S jjrSS.S-S jjrS.S	 jr\	S/S
 j5       r
S0S jrS1S jr  S2       S3S jjrS\4       S4S jjr S5     S6S jjrS.S jrS.S jrS7S jrSS.S8S jjrS.S jrSS.S9S jjrS:S jrS;S jr    S<S jrS.S jrSSS.         S=S jjr\	S>S  j5       rS?S! jr\R<                  " \S"9S@S# j5       r SAS$ jr!SBSCS% jjr"\R<                  " \S"9        SDS& j5       r#\R<                  " \S"9        SES' j5       r$\R<                  " \S"9        SFS( j5       r%S5SGS) jjr&S*r'g)HAudioRecognition}   N)	stt_modelstt_providerc               6   Xl         X l        S U l        S U l        S U l        S U l        S U l        X0l        [        U[        5      (       d  UOS U l
        X@l        XPl        Xl        Xl        [        U[        5      (       a  UOS U l        U R                  S;   U l        SU l        S U l        SU l        S U l        S U l        S U l        [.        R0                  " 5       U l        / U l        SU l        SU l        SU l        S U l        S U l        S U l         [C        5       U l"        S U l#        X`l$        S U l%        S U l&        [N        U l(        [S        5       U l*        US L=(       a    US LU l+        SU l,        S U l-        [.        R0                  " 5       U l.        SU l/        g )Nr   NF )0_session_hooks_audio_input_atask_commit_user_turn_atask_stt_consumer_atask
_vad_atask_end_of_turn_task_endpointingr   r.   _turn_detector_stt_vad
_stt_model_stt_provider_turn_detection_mode_vad_base_turn_detection_user_turn_committed_sample_rate	_speaking_last_final_transcript_time_last_speaking_time_speech_start_timer   Event_final_transcript_received_final_transcript_confidence_audio_transcript_audio_interim_transcript_audio_preflight_transcript_last_language_stt_pipeline_vad_chset_tasks_interruption_atask_interruption_detection_interruption_ch_input_started_atr   _ignore_user_transcript_untilr   _transcript_buffer_interruption_enabled_agent_speaking_user_turn_span_closing_vad_speech_started)
rJ   sessionhooksendpointingr   r   interruption_detectionturn_detectionr   r   s
             r@   r   AudioRecognition.__init__~   s     =ABF$>B 59<@-84>~s4S4SnY]		#)6@QT6U6UN[_!(,(A(A](R%$)!(,9=(15 04 +2--/'9;)!#)+&+-(37268<.1e ?C '=$VZ/3@I*6;g+A+M+aRU]aRa"%*26). r?   )r   r   min_endpointing_delaymax_endpointing_delayc                  [        U5      (       a  Xl        [        U5      (       a  [        U[        5      (       d  UOS U l        [        U[        5      (       a  UOS nU R
                  U:w  a  U R
                  nXPl        U R
                  S;   U l        U R
                  S:X  d  US:X  aY  U R                  (       a9  U R                  R                  5       (       d  U R                  R                  5         S U l        SU l
        g g g g )Nr   manualF)r    r   r   r.   r   r   r   r   donecancelr   )rJ   r   r   r   r   modeprevious_modes          r@   update_optionsAudioRecognition.update_options   s     K   +N##8B>SV8W8W.]aD%/%D%D>$D((D0 $ 9 9,0)040I0I]0Z-,,8MX<U--#55::<< 2299;-1D*05D- =V 1	 $r?   )stt_pipelinec                   U R                  U R                  US9  U R                  U R                  5        U R	                  U R
                  5        g )Npipeline)
update_sttr   
update_vadr   update_interruption_detectionr   )rJ   r   s     r@   startAudioRecognition.start   s:    		L9		"**4+G+GHr?   c                j    U R                  S 5        U R                  S 5        U R                  S 5        g rH   )r   r   r   ri   s    r@   stopAudioRecognition.stop   s(    **40r?   c                    U R                   =(       a0    U R                  S L=(       a    U R                  R                  (       + $ rH   )r   r   closedri   s    r@   adaptive_interruption_active-AudioRecognition.adaptive_interruption_active   s<     && 1%%T11))000	
r?   c                    SU l         U R                  R                  US9  U R                  (       a$  U R                  R                  [        5       5        g g )NT)
started_at)r   r   on_start_of_agent_speechr   r   r   r   )rJ   r   s     r@   r   )AudioRecognition.on_start_of_agent_speech   sG    #22j2I,,!!--.I.KL -r?   c                 ^ ^ T R                   (       a,  T R                  R                  [        R                  " 5       S9  T R                  (       d  ST l         g T R
                  R                  [        5       5        T R                   (       a  [        T R                  5      (       d"  T R                  [        R                  " 5       S9  [        T R                  5      (       d  UO[        UT R                  5      T l	        [        R                  " T R                  5       5      mTR                  U U4S j5        T R                   R#                  T5        ST l         g )Nended_atFc                :   > TR                   R                  T5      $ rH   r   discardry   rJ   tasks    r@   rz   9AudioRecognition.on_end_of_agent_speech.<locals>.<lambda>      T[[-@-@-Fr?   )r   r   on_end_of_agent_speechtimer   r   r   r   r    r   on_end_of_overlap_speechminr   r   _flush_held_transcriptsr   r   add)rJ   ignore_user_transcript_untilr   s   ` @r@   r  'AudioRecognition.on_end_of_agent_speech   s    44diik4J00#(D ))*C*EFD>>??--tyy{-C   B BCC -5t7Y7YZ . &&t'C'C'EFD""#FGKKOOD!$r?   c                    U R                   R                  XR                  S9  U R                  (       a  U R                  (       d  g U R                  R                  [        UUUS95        g )N)r   overlapping)speech_durationuser_speaking_spanr   )r   rO   r   r   r   r   r   )rJ   r   r  r  s       r@   rO   #AudioRecognition.on_start_of_speech  sa     	,,!/C/C 	- 	
 008L8L))) /#5%	
r?   c                    U R                   (       aD  U R                  R                  U[        U5      =(       a    U(       + =(       a    U R                  S9  U R                  XS9  g )N)r   should_ignore)r   r  )r   r   rU   r    r   r  )rJ   r   r  interruptions       r@   rU   !AudioRecognition.on_end_of_speech#  sU     >>..!\*X</?XDDXDX /  	%%x%_r?   c                    U R                   (       a  U R                  (       d  gU(       a  UR                  5       (       a  [        U[        5      (       a\  UR
                  (       aJ  UR
                  R                  [        R                  5      c   UR                  [        R                  S5        O UR                  [        R                  S5        U R                  R                  [        U=(       d    [        R                  " 5       S95        g)zJEnd interruption inference when agent is speaking and overlap speech ends.Nfalser   )r   r   is_recordingr   r   
attributesgetr   ATTR_IS_INTERRUPTIONset_attributer   r   r   r  )rJ   r   r  s      r@   r  )AudioRecognition.on_end_of_overlap_speech3  s     008L8L "4"A"A"C"C,l;;&11*5599+:Z:Z[c&44[5U5UW^_"001Q1QSZ[))'1HTYY[I	
r?   c                  #    U R                   (       a8  [        U R                  5      (       a  U R                  (       a  U R                  c  U R                  5         gSnSn[        U R                  5       H  u  p4UR                  (       d  Ub  [        X5      OUnM(  UR                  S   R                  UR                  S   R                  s=:X  a  S:X  a  O  OU R                  5           gUR                  S   R                  S:  a8  UR                  S   R                  U R                  -   U R                  :  a  SnM  Ub  [        X5      OUnSn  O   Ub(  U(       a!  [        U R                  5      [        U5      S O/ nU R                  5         U H=  n[        R                  " SSUR                  0S9  U R!                  U5      I Sh  vN   M?     g N	7f)zFlush held transcripts whose *end time* is after the ignore_user_transcript_until timestamp.

If the event has no timestamps, we assume it is the same as the next valid event.
NFr   Tz re-emitting held user transcripteventextra)r   r    r   r   r   _reset_interruption_detection	enumeratealternativesr  
start_timeend_timelistintr   r
   r   _on_stt_event)rJ   emit_from_indexshould_flushirK   events_to_emits         r@   r  (AudioRecognition._flush_held_transcriptsK  s     **D>>??**%%-..0&*t667EA??=L=X#o"9^_q!,,0B0K0KPqP224 "++a/OOA&//$2H2HH445 #' >M=X#o"9^_#) 84 *| (()#o*>*@A 	
 	**, BLL2RWW $$R((( ! )s   GGG
Gc                N    U R                   R                  5         [        U l        g)z:Reset relevant states for adaptive interruption detection.N)r   clearr   r   ri   s    r@   r  .AudioRecognition._reset_interruption_detection  s    %%'-6*r?   c                z   U R                   (       d  gU R                  (       a  gUR                  [        R                  R
                  :X  a  [        U l        g[        U R                  5      (       d  gUR                  (       d  g[        U R                  5      (       a  U R                  b  UR                  S   R                  UR                  S   R                  s=:X  a  S:X  dT  O  UR                  S   R                  S:  a5  UR                  S   R                  U R                  -   U R                  :  a  gg)zRTest if the event should be held until the ignore_user_transcript_until timestamp.FTr   )r   r   r   r   SpeechEventTypeSTART_OF_SPEECHr   r   r    r!  r   r"  r#  rI   s     r@   _should_hold_stt_event'AudioRecognition._should_hold_stt_event  s    )) 77c))9991:D.::;;  T++,,
 &&2__Q'22booa6H6Q6QVUVV"--1"--0F0FF001 r?   F)skip_sttc               b   U R                   c'  [        R                  " 5       UR                  -
  U l         UR                  U l        U(       d2  U R
                  b%  U R
                  R                  R                  U5        U R                  b  U R                  R                  U5        U R                  R                  bI  U R                  R                  R                  (       d$  U R                  R                  R                  5         U R                  b  U R                  R                  U5        g g rH   )r   r  durationsample_rater   r   r   r   r   r   amdstarted_on_first_audior   )rJ   framer4  s      r@   
push_audioAudioRecognition.push_audio  s    !!)%)YY[5>>%AD"!--D..:''33E:<<#LL$$U+==(1B1B1J1JMM--/  ,!!--e4 -r?   c                  #    U R                   R                  5         U R                  b  U R                  I S h  vN   U R                  b)  U R                  R	                  5       I S h  vN   S U l        [
        R                  " U R                  6 I S h  vN   U R                  b(  [
        R                  " U R                  5      I S h  vN   U R                  b(  [
        R                  " U R                  5      I S h  vN   U R                  b(  [
        R                  " U R                  5      I S h  vN   U R                  b  U R                  I S h  vN   g g  GN" N N N Ne N2 N7frH   )r   r   r   r   r   r   r   r   r   r   r   r   ri   s    r@   r   AudioRecognition.aclose  s'    ''3....)$$++---!%D!!4;;///##/%%d&>&>?????&%%doo666##/%%d&>&>???!!-(((( .# / . 	0 @ 7 @ )s{   7E*E.E*(E)+E*E 4E*	E"
4E*>E$?4E*3E&4 E*E(E*E* E*"E*$E*&E*(E*r   c                 ^ ^ UT l         Uc  Ub  [        U5      nUb|  [        R                  " T R	                  UR
                  T R                  T R                  S95      T l        UT l        T R                  R                  5         [        T l        S T l        g T R                  bl  [        R                  " [        R                  " T R                  5      5      mTR                  U U4S j5        T R                   R#                  T5        S T l        T R                  bg  [        R                  " T R                  R%                  5       5      mTR                  U U4S j5        T R                   R#                  T5        S T l        g g )N)r   old_pipelineold_consumerc                :   > TR                   R                  T5      $ rH   r   r   s    r@   rz   -AudioRecognition.update_stt.<locals>.<lambda>      1D1DT1Jr?   c                :   > TR                   R                  T5      $ rH   r   r   s    r@   rz   rD    rE  r?   )r   rs   r   r   _stt_consumerr   r   r   r   r-  r   r   r   r   r   r   r   r  r   )rJ   r   r   r   s   `  @r@   r   AudioRecognition.update_stt  s<   	#C(H'.':':""%..!%!3!3!%!9!9 # (D$ "*D##))+1:D.%)D"''3**3+>+>t?W?W+XY&&'JK%+/(!!-**4+=+=+D+D+FG&&'JK%%)"	 .r?   c                L  ^ ^ UT l         U(       al  [        R                  [        R                     " 5       T l        [        R                  " T R                  UT R
                  T R                  5      5      T l	        OT R                  bs  [        R                  " [        R                  " T R                  5      5      mTR                  U U4S j5        T R                  R                  T5        S T l	        S T l        T R                  S L=(       a    T R                   S LT l        g )Nc                :   > TR                   R                  T5      $ rH   r   r   s    r@   rz   -AudioRecognition.update_vad.<locals>.<lambda>  r  r?   )r   r   r}   r   r~   r   r   r   	_vad_taskr   r   r   r   r  r   r   )rJ   r   r   s   ` @r@   r   AudioRecognition.update_vad  s    	88CNN35DL%11sDLL$//BDO __(&&s':':4??'KLD""#FGKKOOD!"DODL ((4N$9N 	"r?   c                   #    U R                   nSU l         U R                  b/  [        R                  " U R                  5      I Sh  vN   SU l        U$  N7f)zDetach the STT pipeline for handoff to another AudioRecognition.

Returns the pipeline (pump task + channels) without stopping it.
The caller is responsible for passing it to the new AudioRecognition
via start(..., stt_pipeline=pipeline).
N)r   r   r   r   )rJ   r   s     r@   
detach_sttAudioRecognition.detach_stt
  sU      %%! ##/%%d&>&>???'+D$ @s   AAAAc                  ^ ^ UT l         Ub  [        R                  [        R                     " 5       T l        [        R                  " T R                  UT R
                  T R                  5      5      T l	        T R                  R                  5         [        T l        S T l        OT R                  bs  [        R                  " [        R                  " T R                  5      5      mTR!                  U U4S j5        T R"                  R%                  T5        S T l	        S T l        T R                   S L=(       a    T R&                  S LT l        g )Nc                :   > TR                   R                  T5      $ rH   r   r   s    r@   rz   @AudioRecognition.update_interruption_detection.<locals>.<lambda>+  r  r?   )r   r   r}   r   InterruptionDataFrameTyper   r   r   _interruption_taskr   r   r-  r   r   r   r   r   r   r  r   r   )rJ   r   r   s   ` @r@   r   .AudioRecognition.update_interruption_detection  s    (>$!-$'HHY-P-P$Q$SD!'.':':''*D,A,A4C[C[(D$
 ##))+1:D.%)D"%%1&&s':':4;S;S'TUD""#FGKKOOD!'+D$$(D! ((4N$9N 	"r?   c                    SU l         SU l        SU l        / U l        SU l        U R
                  nU R                  S 5        U R                  U5        g )Nr   F)r   r   r   r   r   r   r   )rJ   r   s     r@   clear_user_turn AudioRecognition.clear_user_turn4  sM    !#)+&+-(,.)$)! iir?   g       @)stt_flush_durationr-   c                 ^ ^^^^^ [         R                  " 5       nUR                  5       mT R                  (       a  T R                  R                  5       (       a  TR                  S5        T$ SUUU UUU4S jjnSU4S jjnT R                  b  T R                  R                  5         [         R                  " U" 5       5      T l        T R                  R                  U5        T$ )Nr   c            
     Z  >#    TR                   b&  [        R                  " 5       TR                   -
  S:  a  TR                  R                  5         T(       a  TR                  (       a  [        TR                  S-  5      n [        R                  " SU -  TR                  SU S9n[        S[        [        R                  " T
UR                  -  5      5      5      n[        U5       H  nTR                  U5        M      [        R                  " TR                  R!                  5       TS9I S h  vN   TR$                  (       a  TR*                  R-                  [.        R0                  " [.        R2                  R4                  [.        R6                  " [9        S5      TR$                  S9/S95        TR:                   STR$                   3R=                  5       Tl        TR:                  nSTl        TR*                  R?                  5       RA                  5       nTRC                  UT	S9  STl"        TRG                  5       (       d  TRI                  U5        g g  GN+! [        R"                   a7    TR$                  (       a"  [&        R(                  " STTR$                  S	.S
9   GNsf = f7f)Ng      ?g?s     r!   )r7  num_channelssamples_per_channelr   timeoutz+final transcript not received after timeout)transcript_timeoutinterim_transcriptr  r   )languagetext)r   r!   )r-   T)%r   r  r   r-  r   r%  r   r~   maxmathceilr6  ranger<  r   wait_forwaitTimeoutErrorr   r   warningr   r^   r   r   r0  FINAL_TRANSCRIPT
SpeechDatar   r   striprj   copy_run_eou_detectionr   r   
set_result)num_samplessilence_frame
num_framesry   
transcriptchat_ctxaudio_detachedfutrJ   r-   rZ  ra  s         r@   _commit_user_turn<AudioRecognition.commit_user_turn.<locals>._commit_user_turnO  s0    //7		d>>>D
 //557 "d&7&7"%d&7&7#&=">K$'NN#k1$($5$5%&,7	%M "%QDII6H=KaKa6a,b(c!dJ":.6 /!**77<<> 2   --//OO 00AANN)5b)9@^@^&	 --.a0N0N/OPVVX & //J-/D*{{446;;=H##H#D(,D%88::z* K ++ 55I6H6:6T6T#s>   C;J+?0I /I0I 4D&J+I AJ($J+'J((J+c                   > TR                  5       (       a  g U R                  5       (       a  TR                  5         g U R                  5       =n(       a  TR	                  U5        g g rH   )r   	cancelledr   	exceptionset_exception)r   excrz  s     r@   _on_task_done8AudioRecognition.commit_user_turn.<locals>._on_task_done  sL    xxzz~~

(((!!#& )r?   r   )r   zasyncio.Task[None]rm   rn   )r   get_running_loopcreate_futurer   r   is_setrs  r   r   r   r   )	rJ   ry  ra  rZ  r-   loopr{  r  rz  s	   `````   @r@   commit_user_turn!AudioRecognition.commit_user_turn@  s     '')#'#5#5#7yyDMM0022NN2J>	+ >	+@	' ''3((//1'.':':;L;N'O$$$66}E
r?   c                t    U R                   (       a  U R                  S-   U R                   -   $ U R                  $ )zF
Transcript for this turn, including interim transcript if available.
re  )r   r   ri   s    r@   current_transcript#AudioRecognition.current_transcript  s5    
 ))))C/$2P2PPP%%%r?   c           	       #    U R                   S:X  af  U R                  (       aU  U R                  bG  U R                  R                  5       (       d(  UR                  [
        R                  R                  :X  a  g UR                  [
        R                  R                  :w  a  U R                  (       a  U R                  U5      (       ad  [        R                  " SUR                  [        U R                  5      (       a  U R                  OS S.S9  U R                  R!                  U5        g U R                  (       a  U R#                  5       I S h  vN   UR                  [
        R                  R$                  :X  Ga/  UR&                  S   R(                  nUR&                  S   R*                  nUR&                  S   R,                  nU R.                  (       a  U(       a  [1        U5      [2        :  a  X0l        U R4                  R7                  5         U(       d  g U R8                  R;                  UU R<                  (       d  U R                   S:X  a  U R>                  OS S9  U R@                  RB                  b%  U R@                  RB                  RE                  U5        X R.                  S.nU RF                  (       a%  [H        RH                  " 5       U RF                  -
  US	'   [        RJ                  " S
US9  [H        RH                  " 5       U l&        U =RN                  SU 3-  sl'        U RN                  RQ                  5       U l'        U RR                  R!                  U5        U RN                  U RT                  :g  nSU l+        SU l*        U R<                  (       a  U RF                  c  [H        RH                  " 5       U l#        U RX                  (       d  U R                  (       a  U(       at  U R8                  R[                  []        U RN                  U RR                  (       a+  [_        U RR                  5      [1        U RR                  5      -  OSU R`                  S95        U R>                  (       d:  U R8                  Rc                  5       Re                  5       nU Rg                  U5        g g g UR                  [
        R                  Rh                  :X  Ga  U R8                  Rk                  UU R<                  (       d  U R                   S:X  a  U R>                  OS S9  UR&                  S   R(                  nUR&                  S   R*                  nUR&                  S   R,                  nU R.                  (       a  U(       a  [1        U5      [2        :  a  X0l        U(       d  g [        RJ                  " SX R.                  S.S9  [H        RH                  " 5       U l&        U RN                  S-   U-   RQ                  5       U l*        X l+        U R<                  (       a  U RF                  c  [H        RH                  " 5       U l#        U R                   S:w  d  U R                  (       ag  [m        U RR                  5      U/-   nU R8                  R[                  []        U RT                  [_        U5      [1        U5      -  U R`                  S95        g g UR                  [
        R                  R                  :X  af  U R8                  Rk                  UU R<                  (       d  U R                   S:X  a  U R>                  OS S9  UR&                  S   R(                  U l+        g UR                  [
        R                  Rn                  :X  Ga,  U R                   S:X  Ga  [        Rp                  " U Rs                  5       5         U R8                  Ru                  S 5        S S S 5        U R<                  (       aB  U R>                  (       a  [        Rv                  " S5        U Ry                  U R<                  5        SU l        SU l        U R<                  (       a  U RF                  c  [H        RH                  " 5       U l#        U R8                  Rc                  5       Re                  5       nU Rg                  U5        g UR                  [
        R                  Rz                  :X  a  U R                   S:X  a  [        Rp                  " U Rs                  5       5         U R8                  R}                  S 5        S S S 5        SU l        U R`                  c  [H        RH                  " 5       U l0        [H        RH                  " 5       U l#        U R                  b  U R                  R                  5         g g g g  GNN! , (       d  f       GN= f! , (       d  f       N= f7f)Nr   z<holding STT event until ignore_user_transcript_until expires)r  r  r  r   r   r\   )user_transcriptrc  transcript_delayzreceived user transcriptre  r   )r/   r1   r3   z"received user preflight transcriptz@stt end of speech received while user is speaking, resetting vadFT)@r   r   r   r   r   r   r0  INTERIM_TRANSCRIPTRECOGNITION_USAGEr   r2  r   r
   r    r   r   appendr  rn  r!  rd  rc  
confidencer   lenMIN_LANGUAGE_DETECTION_LENGTHr   r   r   r^   r   r   r   r8  _on_transcriptr   r  debugr   r   lstripr   r   r   r   rf   rB   sumr   rj   rq  rr  PREFLIGHT_TRANSCRIPTrZ   r$  END_OF_SPEECHuse_span_ensure_user_turn_spanrU   rm  r   r1  rO   r   )	rJ   rK   rw  rc  r  r  transcript_changedrx  confidence_valss	            r@   r&  AudioRecognition._on_stt_event  s!    %%1))&&.))..0077c11DDD
  77c));;;@Z@Z**2..R!##D$F$FGG 9=8Z8Z!	 ''..r2((22444 77c)):::+00Jq)22H+66J&&S_/LL&.#++//1KK++99 9 9U B 	 ,  }}  ,!!00<8BPcPc$dE'',0IIK$:R:R,R()LL35A/3yy{D,""*&66"%)%;%;%B%B%DD"--44Z@!%!7!74;[;[![-/D*/1D,99 8 8 @ ,099;(,,0I0I%KK881+/+A+A $(#D#D !$D$E$E F"%d&G&G"H!I &'040G0G	 ~~#{{<<>CCEH++H5 & 1J& WW++@@@KK--99 9 9U B 	 .  +00Jq)22H+66J&&S_/LL&.#LL4*4BUBUV 04yy{D,040F0F0Lz0Y/a/a/cD,-7*99 8 8 @+/99;(((H48Q8Q"&t'H'H"IZL"X44-'+'G'G.1/.BSEY.Y,0,C,C 9R WW++>>>KK--99 9 9U B 	 .  .0__Q-?-D-DD*WW++999d>W>W[`>` ; ; =>,,T2 ? yy>>NNZ 		*"DN(,D%99 8 8 @+/99;({{446;;=H##H-WW++;;;@Y@Y]b@b ; ; =>..t4 ? "DN&&.*.))+''+yy{D$%%1&&--/ 2 Ac;_ 5p ?>0 ?>sE   EgfY#g4f!D7gf3#A<g!
f0+g3
g=gr   c                L  #    UR                   [        R                  R                  :X  a  [        R                  " 5       UR
                  -
  UR                  -
  nU R                  (       d  X l        SU l        [        R                  " U R                  US95         U R                  R                  U5        S S S 5        SU l        U R                  b  U R                  R!                  5         U R"                  R$                  b%  U R"                  R$                  R'                  5         g g UR                   [        R                  R(                  :X  a|  U R                  R+                  U5        UR,                  S:  aP  [        R                  " 5       U l        U R                  c(  [        R                  " 5       UR,                  -
  U l        g g g UR                   [        R                  R0                  :X  Ga	  [        R                  " U R                  5       5         U R                  R3                  U5        S S S 5        SU l        SU l        U R4                  (       d!  U R6                  S:X  aJ  U R8                  (       a9  U R                  R;                  5       R=                  5       nU R?                  U5        U R"                  R$                  b0  U R"                  R$                  RA                  URB                  5        g g g ! , (       d  f       GNQ= f! , (       d  f       N= f7f)NTr"          Fr   )"r   r   VADEventTyper1  r  r  inference_durationr   r   r
   r  r  r   rO   r   r   r   r   r8  _on_user_speech_startedINFERENCE_DONErR   raw_accumulated_speechr   r  rU   r   r   r   rj   rq  rr  _on_user_speech_endedsilence_duration)rJ   rK   speech_start_timerx  s       r@   _on_vad_eventAudioRecognition._on_vad_eventb  s=    77c&&666 $		b.@.@ @2CXCX X++*;'+/( ; ;GX ; YZ..r2 [ "DN%%1&&--/}}  ,!!99; - WW((777KK--b1 ((3.+/99;(**2.2iikB<U<U.UD+ 3 / WW((666 ; ; =>,,R0 ? (-D$"DN,,))U2t7P7P;;88:??A''1}}  ,!!778K8KL - 7+ [Z, ?>s8   BL$L7E$L$L7C
L$
LL$
L!L$c                f   #    UR                   (       a  U R                  R                  U5        g g 7frH   )is_interruptionr   rL   rI   s     r@   _on_overlap_speech_event)AudioRecognition._on_overlap_speech_event  s%     KK''+ s   /1c                X  ^ ^^^ T R                   (       a"  T R                  (       d  T R                  S:w  a  g TR                  5       mTR	                  ST R                  S9  T R                  (       a  T R                  S:w  a  T R
                  OS m[        R                  " [        S9   S       SUU UU4S jjj5       nT R                  b  T R                  R                  5         [        R                  " U" T R                  T R                  T R                  5      5      T l	        g )Nr   user)rolecontentr   c                  >#    TR                   R                  nTR                  5       nTGb  TR                  TR                  5      I S h  vN (       d#  [
        R                  " STR                  5        GOu[        R                  " U5         [        R                  " S5       nSnS n TR                  T5      I S h  vN nTR                  TR                  5      I S h  vN nUb  Xg:  a  TR                   R                  nUR!                  ["        R$                  [&        R(                  " [*        R,                  " TR.                  [0        * S  5      R3                  SSSSSS9R5                  SSSSS95      ["        R6                  U["        R8                  U=(       d    S["        R:                  U["        R<                  TR                  =(       d    S	05        S S S 5        S S S 5        UnU (       a  X[>        R>                  " 5       -
  -  nUS:  a6   [@        RB                  " TRD                  RG                  5       US
9I S h  vN   TRJ                  (       a+  [M        TRJ                  5      [O        TRJ                  5      -  OSn	S n
S nS nS nUb0  U b-  Ub*  Un
U n[Q        X-
  S5      n[>        R>                  " 5       U -
  nTRR                  RU                  [W        TTRX                  U	U=(       d    SUU
US95      nU(       a  UR!                  ["        RZ                  TRX                  ["        R\                  U	["        R^                  U=(       d    S["        R`                  U=(       d    S05        URc                  5         S Tl2        S	Tl,        / Tl%        S Tl3        TRh                  U :X  a  S Tl5        STl6        S Tl4        STl7        g  GN GN GN! [         a    [
        R                  " S5         GNf = f! , (       d  f       GN'= f! , (       d  f       GN1= f GN! [@        RH                   a     GNf = f7f)Nz*Turn detector does not support language %seou_detectionr  zError predicting end of turnT)exclude_function_callexclude_instructionsexclude_empty_messageexclude_handoffexclude_config_update)exclude_audioexclude_imageexclude_timestampexclude_metricsr   r   r_  )r-   r/   r1   r5   r6   r3   r4   F)8r   	min_delayr  supports_languager   r   rb   r
   r  r   start_as_current_spanpredict_end_of_turnunlikely_threshold	max_delay	Exceptionr  set_attributesr   ATTR_CHAT_CTXjsondumpsr   ChatContextitems_EOU_MAX_HISTORY_TURNSrq  to_dictATTR_EOU_PROBABILITYATTR_EOU_UNLIKELY_THRESHOLDATTR_EOU_DELAYATTR_EOU_LANGUAGEr  r   rj  r   rk  rl  r   r  r  rf  r   rc   r*   r   ATTR_USER_TRANSCRIPTATTR_TRANSCRIPT_CONFIDENCEATTR_TRANSCRIPTION_DELAYATTR_END_OF_TURN_DELAYendr   r   r   r   r   r   )last_speaking_timelast_final_transcript_timer  endpointing_delayuser_turn_spaneou_detection_spanend_of_turn_probabilityr  extra_sleepconfidence_avgr3   r4   r5   r6   	committedrx  rJ   r-   turn_detectors                  r@   _bounce_eou_task=AudioRecognition._run_eou_detection.<locals>._bounce_eou_task  s     !% 1 1 ; ;!88:N(*<<T=P=PQQQKK LdNaNab ~644_EI[ 36/;?*M<I<]<] (= 73 8E7W7W $ 3 38 2. !3 >$;$P484E4E4O4O 1 +99 + 9 94::$'OOHNNDZCZC[4\$]%)T>B=A>B8<>B &* && &-W6:6::>8<	 &- &&<"  !, @ @BY + G GI[I`_` + : :<M + = =t?R?R?XVX)) F 7\ ,K!DIIK??Q!**4==+=+=+?UUU 44 D556T=^=^9__  #'"&"& $
 +6&2%1&7#&8#&)*D*Y[\&]#$(IIK2D$D!22)#'#9#9*8(;(@q&7(;(;
I --#88$:P:P#>>#<<>Q>VUV#::<M<RQR	 ""$'+$ *,&461370 ++/AA.2D+/4D,/3D,(-D%k R72  ) M",,-KLM# FE 76h V++ s   A	Q OAQ P&O>,O O"O#O$"OCO>P&1Q 0P% P"	P% FQ OO O;7O>:O;;O>>
P	P
PQ "P% %P=9Q <P==Q )NNN)r  r2   r  r2   r  r2   rm   rn   )r   r   r   rq  add_messager   r   r   r   r   r   r   r   r   r   r   )rJ   rx  r-   r  r  s   ``` @r@   rr  #AudioRecognition._run_eou_detection  s#   99T338Q8QU]8]==?&$2H2HI %%$*C*Cx*O  	 
		V	,/37;.2}	. ,}	.(4}	.  ,}	. 	}	. }	. 
-}	.~ !!-""))+ ")!4!4((00''"
r?   c                   #    Ub  UR                  5       I Sh  vN   Ub  [        R                  " U5      I Sh  vN   U  Sh  vN nU R                  U5      I Sh  vN   M$   NK N, N# N
 g7f)z5Consume STT events from the pump. Swapped on handoff.N)r   r   r   r&  )rJ   r   rA  rB  rK   s        r@   rG  AudioRecognition._stt_consumer-  sn      #%%'''#%%l333  	)"$$R((( ( 4	)( !sU   A/A% A/A'A/A-A)A-	A/A+A/'A/)A-+A/-A/c                   ^^#    Ub  [         R                  " U5      I S h  vN   UR                  " 5       m[        R                  " [
        S9SUU4S jj5       n[        R                  " U" 5       5      n T  S h  vN nU R                  U5      I S h  vN   M$   N{ N! N

 [         R                  " U5      I S h  vN    TR                  5       I S h  vN    U R                  (       ai  [        R                  " U R                  5       5         U R                  R                  S 5        S S S 5        O! , (       d  f       O= fSU l
        SU l        g g ! [         R                  " U5      I S h  vN    TR                  5       I S h  vN    U R                  (       ai  [        R                  " U R                  5       5         U R                  R                  S 5        S S S 5        O! , (       d  f       O= fSU l
        SU l        f f = f7f)Nr   c                 P   >#    T  S h  vN n TR                  U 5        M   N
 g 7frH   
push_framer;  audio_inputstreams    r@   _forward,AudioRecognition._vad_task.<locals>._forwardK  %     * )e!!%(){   &$"$&$&Fr   )r   r   r  r   r   r   r   r   r  r   r   r
   r  r  r   rU   r   )rJ   r   r  r   r  forward_taskrK   r  s     `    @r@   rL  AudioRecognition._vad_task?  s     %%d+++			V	,	) 
-	) **8:6	1" -b((,,, ,-, # %%l333--/!! ~~^^D$?$?$ABKK006 CBB!&+0(	 	 %%l333--/!! ~~^^D$?$?$ABKK006 CBB!&+0(	 s   HBAH7E 9B#=B>B#E B!E HB#!E #E $H=C >HC:HD6-	H6
E HH1E42H
F:HG*!	H*
G84HHc                6  ^^#    Ub  [         R                  " U5      I S h  vN   UR                  5       m[        R                  " [
        S9SUU4S jj5       n[        R                  " U" 5       5      n T  S h  vN nU R                  U5      I S h  vN   M$   Nz N! N

 [         R                  " U5      I S h  vN    TR                  5       I S h  vN    g ! [         R                  " U5      I S h  vN    TR                  5       I S h  vN    f = f7f)Nr   c                 P   >#    T  S h  vN n TR                  U 5        M   N
 g 7frH   r  r  s    r@   r  5AudioRecognition._interruption_task.<locals>._forwardl  r  r  r   )
r   r   r  r   r   r   r   r   r  r   )rJ   r   r  r   r  r  rK   r  s     `    @r@   rU  #AudioRecognition._interruption_task`  s      %%d+++'..0			V	,	) 
-	) **8:6	"" 8b33B777 ,87 # %%l333--/!! %%l333--/!!s   DBAD6C 8B"<B=B" C B C DB" C "C #D<B?=DCDD6C97DDDDc                   U R                   (       a+  U R                   R                  5       (       a  U R                   $ U(       a  [        US-  5      OS n[        R                  " SUS9U l         U R
                  R                  =n(       a1  UR                  (       a   [        U R                   UR                  5        U R                  (       a4  U R                   R                  [        R                  U R                  5        U R                  (       a4  U R                   R                  [        R                  U R                  5        U R                   $ )Ni ʚ;	user_turnr  )r   r  r%  r   
start_spanr   _room_iolinked_participantr#   r   r  r   ATTR_GEN_AI_REQUEST_MODELr   ATTR_GEN_AI_PROVIDER_NAME)rJ   r"  start_time_nsroom_ios       r@   r  'AudioRecognition._ensure_user_turn_spanz  s    D$8$8$E$E$G$G''';EJ674%00W}}---G-73M3M'(<(<g>X>XY ??  ..55t   ..55t7I7I ###r?   ))r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   )r   r&   r   rE   r   r$   r   io.STTNode | Noner   vad.VAD | Noner   -inference.AdaptiveInterruptionDetector | Noner   zTurnDetectionMode | Noner   
str | Noner   r  rm   rn   )
r   zNotGivenOr[BaseEndpointing]r   z$NotGivenOr[TurnDetectionMode | None]r   NotGivenOr[float]r   r  rm   rn   )r   _STTPipeline | Nonerm   rn   r   )rm   r,   )r   r0   rm   rn   )r  r0   rm   rn   )r  N)r   r0   r  r0   r  trace.Span | Nonerm   rn   )r   r0   r  r
  r  zNotGivenOr[bool]rm   rn   rH   )r   r0   r  r
  rm   rn   )rK   rp   rm   r,   )r;  zrtc.AudioFramer4  r,   rm   rn   )r   r  r   r	  rm   rn   )r   r  rm   rn   )rm   r	  )r   r  rm   rn   )
ry  r,   ra  r0   rZ  r0   r-   r,   rm   zasyncio.Future[str])rm   r.   )rK   rp   rm   rn   ro   rl   )F)rx  rq   r-   r,   rm   rn   )r   r   rA  r	  rB  asyncio.Task[None] | Nonerm   rn   )r   zvad.VADr  zAsyncIterable[rtc.AudioFrame]r   r  rm   rn   )r   z&inference.AdaptiveInterruptionDetectorr  z2AsyncIterable[inference.InterruptionDataFrameType]r   r  rm   rn   )r"  r2   rm   z
trace.Span)(r9   r:   r;   r<   r   r   r   r   r   r   r   r   r  rO   rU   r  r  r  r2  r<  r   r   r   rO  r   rX  r  r  r&  r   r   r   r  r  rr  rG  rL  rU  r  r>   r7   r?   r@   r   r   }   s@    !%#'@/@/  	@/
 %@/ @/ @/ !N@/ 1@/ @/ !@/ 
@/J 4=?H3<3<6 16 =	6  16  16 
68 <@ I
1
 
 
M%< "%04	

 
 .	

 

, 15)2	`` .` '	`
 
`& 15

 .
 
	
06)p7
&P EJ 5")0 UY *>
$"
&S
	
2
" %( \ \ "	\
 "\ \ 
\| & &y0v (*M )*MX,X
t ()+) *) 0	)
 
) ))" (11 31 (	1
 
1 )1@ (" F" H" (	"
 
" )"2$ $r?   r   )>
__future__r   r   r  rg  r  collectionsr   collections.abcr   dataclassesr   typingr   r   r	   opentelemetryr
   opentelemetry.sdk.tracer   livekitr   r   r   r   r   r   r   inference.interruptionr   r   r   r   rc  r   logr   r   	telemetryr   r   typesr   r   r   r    r"   _utilsr#   r   r$   turnr%   agent_sessionr&   r  r  r*   rB   rE   rs   r   r7   r?   r@   <module>r     s    "      ) ! / /  0  . .  $   + ) !  / ( 8+ !   
$ 
$ 
$ & & &	8x 	8.3 .3bQ$ Q$r?   