
    /j3                       S SK Jr  S SKrS SKrS SKJr  S SKJrJrJ	r	  SSK
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  SSKJr  SSKJr  SSKJr  SSKJ r   \ " S S5      5       r!\ " S S5      5       r" " S S5      r#g)    )annotationsN)	dataclass)AnyAsyncIteratorOptional   )	FfiClient	FfiHandle)audio_frame_pb2)ffi_pb2)TrackSource)	RingQueuetask_done_logger)
AudioFrame)logger)Participant)Track)FrameProcessorc                  $    \ rS rSr% SrS\S'   Srg)AudioFrameEvent"   zmAn event representing a received audio frame.

Attributes:
    frame (AudioFrame): The received audio frame.
r   frame N)__name__
__module____qualname____firstlineno____doc____annotations____static_attributes__r       I/app/agent/.venv/lib/python3.13/site-packages/livekit/rtc/audio_stream.pyr   r   "   s     r!   r   c                  *    \ rS rSr% S\S'   S\S'   Srg)NoiseCancellationOptions-   str	module_idzdict[str, Any]optionsr   N)r   r   r   r   r   r    r   r!   r"   r$   r$   -   s    Nr!   r$   c                  4   \ rS rSrSr      S               SS jjr\SSSSSSS.                 SS	 jj5       r\SSSSSSS.               SS
 jj5       rSS jr	SS jr
      SS jrS rSS jrSS jrSS jrSS jrSrg)AudioStream3   a?  An asynchronous audio stream for receiving audio frames from a participant or track.

The `AudioStream` class provides an asynchronous iterator over audio frames received from
a specific track or participant. It allows you to receive audio frames in real-time with
customizable sample rates and channel configurations.
Nr   逻  r   c                <   Xl         X@l        XPl        X`l        U=(       d    [        R
                  " 5       U l        [        R                  R                  R                  U R                  S S9U l        [        U5      U l        SU l        SU l        SU l        [#        U[$        5      (       a#  UR&                  U l        UR(                  U l        O[#        U[*        5      (       a  Xpl        U R                  R-                  U R/                  5       5      U l        U R0                  R3                  [4        5        Sn	SU;   a  U R7                  US   US   S9n	OU R9                  5       n	[;        U	R<                  R>                  5      U l         U	RB                  U l"        g)a  Initialize an `AudioStream` instance.

Args:
    track (Optional[Track]): The audio track from which to receive audio. If not provided,
        you must specify `participant` and `track_source` in `kwargs`.
    loop (Optional[asyncio.AbstractEventLoop], optional): The event loop to use.
        Defaults to the current event loop.
    capacity (int, optional): The capacity of the internal frame queue. Defaults to 0 (unbounded).
    sample_rate (int, optional): The sample rate for the audio stream in Hz.
        Defaults to 48000.
    num_channels (int, optional): The number of audio channels. Defaults to 1.
    noise_cancellation (Optional[NoiseCancellationOptions | FrameProcessor[AudioFrame]], optional):
        If noise cancellation is used, pass a `NoiseCancellationOptions` or `FrameProcessor[AudioFrame]` instance
        created by the noise cancellation module.

Example:
    ```python
    audio_stream = AudioStream(
        track=audio_track,
        sample_rate=44100,
        num_channels=2,
    )

    audio_stream = AudioStream.from_track(
        track=audio_track,
        sample_rate=44100,
        num_channels=2,
    )
    ```
c                *    U R                  S5      S:H  $ )Nmessageaudio_stream_event)
WhichOneof)es    r"   <lambda>&AudioStream.__init__.<locals>.<lambda>m   s    Y 7;O Or!   )	filter_fnNparticipanttrack_source)r6   r7   )#_track_sample_rate_num_channels_frame_size_msasyncioget_event_loop_loopr	   instancequeue	subscribe
_ffi_queuer   _queue_audio_filter_module_audio_filter_options
_processor
isinstancer$   r'   r(   r   create_task_run_taskadd_done_callbackr   %_create_owned_stream_from_participant_create_owned_streamr
   handleid_ffi_handleinfo_info)
selftrackloopcapacitysample_ratenum_channelsframe_size_msnoise_cancellationkwargsstreams
             r"   __init__AudioStream.__init__;   sW   R %*')+5W335
 $,,22<<JJO = 
 :C89L04!<@"=A(*BCC(:(D(DD%);)C)CD&*N;;0OZZ++DIIK8


$$%56F"??"=1~@V @ F ..0F$V]]%5%56[[
r!   )rU   rV   rW   rX   rY   rZ   c               $    [        UUUUSUUUUS9	$ )a  Create an `AudioStream` from a participant's audio track.

Args:
    participant (Participant): The participant from whom to receive audio.
    track_source (TrackSource.ValueType): The source of the audio track (e.g., microphone, screen share).
    loop (Optional[asyncio.AbstractEventLoop], optional): The event loop to use. Defaults to the current event loop.
    capacity (int, optional): The capacity of the internal frame queue. Defaults to 0 (unbounded).
    sample_rate (int, optional): The sample rate for the audio stream in Hz. Defaults to 48000.
    num_channels (int, optional): The number of audio channels. Defaults to 1.
    noise_cancellation (Optional[NoiseCancellationOptions], optional):
        If noise cancellation is used, pass a `NoiseCancellationOptions` instance
        created by the noise cancellation module.

Returns:
    AudioStream: An instance of `AudioStream` that can be used to receive audio frames.

Example:
    ```python
    audio_stream = AudioStream.from_participant(
        participant=participant,
        track_source=TrackSource.MICROPHONE,
        sample_rate=24000,
        num_channels=1,
    )
    ```
N)	r6   r7   rU   rV   rT   rW   rX   rZ   rY   r*   )	clsr6   r7   rU   rV   rW   rX   rY   rZ   s	            r"   from_participantAudioStream.from_participant   s-    N #%#%1'

 
	
r!   c          
          [        UUUUUUUS9$ )a  Create an `AudioStream` from an existing audio track.

Args:
    track (Track): The audio track from which to receive audio.
    loop (Optional[asyncio.AbstractEventLoop], optional): The event loop to use. Defaults to the current event loop.
    capacity (int, optional): The capacity of the internal frame queue. Defaults to 0 (unbounded).
    sample_rate (int, optional): The sample rate for the audio stream in Hz. Defaults to 48000.
    num_channels (int, optional): The number of audio channels. Defaults to 1.
    noise_cancellation (Optional[NoiseCancellationOptions], optional):
        If noise cancellation is used, pass a `NoiseCancellationOptions` instance
        created by the noise cancellation module.

Returns:
    AudioStream: An instance of `AudioStream` that can be used to receive audio frames.

Example:
    ```python
    audio_stream = AudioStream.from_track(
        track=audio_track,
        sample_rate=44100,
        num_channels=2,
    )
    ```
)rT   rU   rV   rW   rX   rZ   rY   r`   )ra   rT   rU   rV   rW   rX   rY   rZ   s           r"   
from_trackAudioStream.from_track   s'    H #%1'
 	
r!   c                j    [         R                  R                  R                  U R                  5        g N)r	   r?   r@   unsubscriberB   rS   s    r"   __del__AudioStream.__del__   s       ,,T__=r!   c                   U R                   c   e[        R                  " 5       nUR                  nU R                   R                  R
                  Ul        U R                  Ul        U R                  Ul
        SUl        U R                  (       a  U R                  Ul        [        R                  R                   Ul        U R$                  b  U R$                  Ul        U R(                  b%  [*        R,                  " U R(                  5      Ul        [0        R2                  R5                  U5      nUR                  R6                  $ Nr   )r8   	proto_ffi
FfiRequestnew_audio_streamrP   rN   track_handler9   rW   r:   rX   queue_size_framesr;   rY   proto_audio_frameAudioStreamTypeAUDIO_STREAM_NATIVEtyperD   audio_filter_module_idrE   jsondumpsaudio_filter_optionsr	   r?   requestr\   )rS   reqrq   resps       r"   rM    AudioStream._create_owned_stream   s    {{&&&""$//(,(?(?(F(F%'+'8'8$(,(:(:%-.*-1-@-@* 1 A A U U$$06:6O6O3%%148JJt?Y?Y4Z1!!))#.$$+++r!   c                d   [         R                  " 5       nUR                  nUR                  R                  Ul        U R                  Ul        U R                  Ul	        SUl
        [        R                  R                  Ul        X$l        U R                   (       a  U R                   Ul        U R$                  b  U R$                  Ul        U R(                  b%  [*        R,                  " U R(                  5      Ul        [0        R2                  R5                  U5      nUR                  R6                  $ rn   )ro   rp   audio_stream_from_participantrP   rN   participant_handler9   rW   r:   rX   rs   rt   ru   rv   rw   r7   r;   rY   rD   rx   rE   ry   rz   r{   r	   r?   r|   r\   )rS   r6   r7   r}   r   r~   s         r"   rL   1AudioStream._create_owned_stream_from_participant   s     ""$(+(I(I%;F;R;R;Y;Y%8484E4E%1595G5G%2:;%7->-N-N-b-b%*5A2:>:M:M)7$$0CGC\C\)@%%1AE**B)> !!))#.11888r!   c                  #     U R                   R                  U R                  5      I S h  vN nUR                  nUR	                  S5      (       a  UR
                  R                  n[        R                  " U5      nU R                  b7  U R                  R                  (       a   U R                  R                  U5      n[        U5      nU R                   R#                  U5        O2UR	                  S5      (       a  U R                   R#                  S 5        OGM  [$        R&                  R(                  R+                  U R                   5        g  GN'! [         a    [        R                  " SSS9   Nf = f7f)NTframe_receivedz7Frame processing failed, passing through original frame)exc_infoeos)rB   wait_for	_is_eventr0   HasFieldr   r   r   _from_owned_inforF   enabled_process	Exceptionr   warningr   rC   putr	   r?   r@   ri   )rS   eventaudio_eventowned_buffer_infor   s        r"   rI   AudioStream._run  s    //224>>BBE>C>V>VK##$455$/$>$>$D$D!"334EF??.4??3J3J $ 8 8 ? (.&%%e,,%' * 	  ,,T__=) C % U%)s5   *E;EA:E;(E BE;E85E;7E88E;c                l   #    U R                   R                  5         U R                  I Sh  vN   g N7f)zAsynchronously close the audio stream.

This method cleans up resources associated with the audio stream and waits for
any pending operations to complete.
N)rP   disposerJ   rj   s    r"   acloseAudioStream.aclose,  s&      	  "jjs   *424c                \    UR                   R                  U R                  R                  :H  $ rh   )r0   stream_handlerP   rN   )rS   r2   s     r"   r   AudioStream._is_event5  s%    ##11T5E5E5L5LLLr!   c                    U $ rh   r   rj   s    r"   	__aiter__AudioStream.__aiter__8  s    r!   c                   #    U R                   R                  5       (       a  [        eU R                  R	                  5       I S h  vN nUc  [        eU$  N7frh   )rJ   doneStopAsyncIterationrC   get)rS   items     r"   	__anext__AudioStream.__anext__;  sD     ::??$$[[__&&<$$	 's   AAAA)rD   rE   rP   rB   r;   rR   r>   r:   rF   rC   r9   rJ   r8   )Nr   r,   r   NN)rT   r   rU   #Optional[asyncio.AbstractEventLoop]rV   intrW   r   rX   r   rY   
int | NonerZ   ?Optional[NoiseCancellationOptions | FrameProcessor[AudioFrame]]returnNone)r6   r   r7   TrackSource.ValueTyperU   r   rV   r   rW   r   rX   r   rY   r   rZ   r   r   r*   )rT   r   rU   r   rV   r   rW   r   rX   r   rY   r   rZ   r   r   r*   )r   r   )r   r   )r6   r   r7   r   r   r   )r2   zproto_ffi.FfiEventr   bool)r   zAsyncIterator[AudioFrameEvent])r   r   )r   r   r   r   r   r]   classmethodrb   re   rk   rM   rL   rI   r   r   r   r   r    r   r!   r"   r*   r*   3   s    59 $(^bJ!J! 2J! 	J!
 J! J! "J! \J! 
J!X  59 $(^b0
 !0
 ,	0

 20
 0
 0
 0
 "0
 \0
 
0
 0
d 
 59 $(^b+
 +
 2	+

 +
 +
 +
 "+
 \+
 
+
 +
Z>,$9&96K9	9.>0Mr!   r*   )$
__future__r   r<   ry   dataclassesr   typingr   r   r   _ffi_clientr	   r
   _protor   rt   r   ro   _proto.track_pb2r   _utilsr   r   audio_framer   logr   r6   r   rT   r   frame_processorr   r   r$   r*   r   r!   r"   <module>r      su    #   ! / / - 8 ( ) / #  $  +      
P Pr!   