
    qi,                        d Z ddlZddlZddlmZ ddlmZ 	 ddlZej                  j                  ej                  j                  ej                  j                  ej                  j                   ej                  j"                  ej                  j$                  dZej(                  j*                  ej(                  j,                  ej(                  j.                  ej(                  j0                  ej(                  j2                  d	Zd
efdZdefdZ G d d      Zy# e$ r7Z	 ej                  de	         ej                  d        ede	       dZ	[	ww xY w)z)Krisp Instance manager for pipecat audio.    N)Lock)loggerzException: zDIn order to use the Krisp instance, you need to install krisp_audio.zMissing module: )i@  i>  i]  i }  iD  i  )
                sample_ratec                     | t         vrEdj                  d t        t         j                               D              }t	        d|  d| d      t         |    S )a   Convert integer sample rate to Krisp SDK enum value.

    Args:
        sample_rate: Sample rate in Hz (e.g., 16000, 24000, 48000).

    Returns:
        Corresponding Krisp SDK SampleRate enum value.

    Raises:
        ValueError: If the sample rate is not supported by Krisp SDK.
    , c              3   2   K   | ]  }t        |        y wNstr).0rates     N/opt/pipecat/venv/lib/python3.12/site-packages/pipecat/audio/krisp_instance.py	<genexpr>z+int_to_krisp_sample_rate.<locals>.<genexpr>7   s     #\$CI#\   zUnsupported sample rate: z Hz. Supported rates: z Hz)KRISP_SAMPLE_RATESjoinsortedkeys
ValueError)r
   supported_ratess     r   int_to_krisp_sample_rater   *   s_     ,,))#\&ASAXAXAZ:[#\\'}4J?J[[^_
 	
 k**    frame_duration_msc                     | t         vrEdj                  d t        t         j                               D              }t	        d|  d| d      t         |    S )a3  Convert integer frame duration to Krisp SDK enum value.

    Args:
        frame_duration_ms: Frame duration in milliseconds (e.g., 10, 20, 30).

    Returns:
        Corresponding Krisp SDK FrameDuration enum value.

    Raises:
        ValueError: If the frame duration is not supported by Krisp SDK.
    r   c              3   2   K   | ]  }t        |        y wr   r   )r   durations     r   r   z.int_to_krisp_frame_duration.<locals>.<genexpr>K   s      (
&CM(
r   zUnsupported frame duration: z ms. Supported durations: z ms)KRISP_FRAME_DURATIONSr   r   r   r   )r   supported_durationss     r   int_to_krisp_frame_durationr$   >   sp      55"ii (
*01F1K1K1M*N(
 
 *+<*= >$$7#8=
 	
 !!233r   c                       e Zd ZdZdZ e       ZdZed        Z	ed        Z
eddefd       Zed        Zed	efd
       Zed	efd       Zed        Zy)KrispVivaSDKManagerz=Singleton manager for Krisp VIVA SDK with reference counting.Fr   c                 :    t        j                  d|  d|        y)z(Callback for Krisp SDK licensing errors.zKrisp licensing error: z - N)r   error)r(   error_messages     r   _license_callbackz%KrispVivaSDKManager._license_callback\   s     	.ugSHIr   c                 :    t        j                  d| d|         y)z+Thread-safe callback for Krisp SDK logging.[z] N)r   info)log_message	log_levels     r   _log_callbackz!KrispVivaSDKManager._log_callbacka   s     	a	{"[M23r   api_keyc           	         | j                   5  | j                  dk(  r	 |xs  t        j                  j	                  dd      }	 t        j                  d|| j                  | j                  t
        j                  j                         d| _        t        j                         }t        j                  d|j                    d|j"                   d|j$                          t'        j(                  | j*                         | xj                  d
z  c_        t        j                  d| j                          d	d	d	       y	# t        $ r< t        j                  d| j                  t
        j                  j                         Y w xY w# t,        $ r%}d| _        t        j.                  d|         d	}~ww xY w# 1 sw Y   y	xY w)ab  Acquire a reference to the SDK (initializes if needed).

        Call this when creating a filter instance.

        Args:
            api_key: Krisp SDK API key. If empty, falls back to the
                KRISP_VIVA_API_KEY environment variable.

        Raises:
            Exception: If SDK initialization fails (propagated from krisp_audio)
        r   KRISP_VIVA_API_KEY Tz.Krisp Audio Python SDK initialized - Version: .Fz!Krisp SDK initialization failed: N   Krisp SDK reference count: )_lock_reference_countosenvirongetkrisp_audio
globalInitr*   r0   LogLevelOff	TypeError_initialized
getVersionr   debugmajorminorpatchatexitregister_force_cleanup	Exceptionr(   )clsr1   keySDK_VERSIONes        r   acquirezKrispVivaSDKManager.acquiref   s    YY #	O##q(!MRZZ^^4H"%MC`#..11--'0044 (,C$"-"8"8":KLLH&,,-Q{/@/@.A;CTCTBUW OOC$6$67   A% LL6s7K7K6LMNG#	O #	O % `#..r33D3DkFZFZF^F^_` ! ',C$LL#DQC!HI;#	O #	OsU   F7$FAD>A6F>7F7>AF FFF	F4 F//F44F77G c                    | j                   5  | j                  dkD  r| xj                  dz  c_        t        j                  d| j                          | j                  dk(  r=| j                  r1	 t        j                          d| _        t        j                  d       ddd       y# t        $ r)}t        j                  d|        d| _        Y d}~6d}~ww xY w# 1 sw Y   yxY w)z{Release a reference to the SDK (destroys if last reference).

        Call this when destroying a filter instance.
        r   r6   r7   Fz3Krisp Audio SDK destroyed (all references released)z Error during Krisp SDK cleanup: N)	r8   r9   r   rD   rB   r=   globalDestroyrK   r(   rL   rO   s     r   releasezKrispVivaSDKManager.release   s     YY 	1##a'$$)$:3;O;O:PQR ''1,1A1A1#113+0(%Z[	1 	1 % 1'Gs%KL+0((1	1 	1s0   A"C00B))	C2CCCCC'returnc                 ^    | j                   5  | j                  cddd       S # 1 sw Y   yxY w)zwGet the current reference count.

        Returns:
            Current number of active references to the SDK.
        N)r8   r9   rL   s    r   get_reference_countz'KrispVivaSDKManager.get_reference_count   s)     YY 	(''	( 	( 	(   #,c                 ^    | j                   5  | j                  cddd       S # 1 sw Y   yxY w)z~Check if the SDK is currently initialized.

        Returns:
            True if SDK is initialized, False otherwise.
        N)r8   rB   rW   s    r   is_initializedz"KrispVivaSDKManager.is_initialized   s)     YY 	$##	$ 	$ 	$rY   c                 8   | j                   5  | j                  r?	 t        j                  d| j                   d       t        j                          d| _        ddd       y# t        $ r"}t        j                  d|        Y d}~/d}~ww xY w# 1 sw Y   yxY w)z)Force cleanup on program exit (failsafe).z0Force cleaning up Krisp SDK at exit (ref count: )Fz'Error during forced Krisp SDK cleanup: N)	r8   rB   r   warningr9   r=   rR   rK   r(   rS   s     r   rJ   z"KrispVivaSDKManager._force_cleanup   s     YY 		PPNNJ3K_K_J``ab  --/',C$		P 		P ! PLL#J1#!NOOP		P 		Ps.   B>A""	B+BBBBBN)r4   )__name__
__module____qualname____doc__rB   r   r8   r9   staticmethodr*   r0   classmethodr   rP   rT   intrX   boolr[   rJ    r   r   r&   r&   U   s    GLFEJ J 4 4 /Oc /O /Ob 1 1( (C ( ( $t $ $ P Pr   r&   )rb   rH   r:   	threadingr   logurur   r=   ModuleNotFoundErrorrO   r(   rK   SamplingRateSr8000Hz	Sr16000Hz	Sr24000Hz	Sr32000Hz	Sr44100Hz	Sr48000Hzr   FrameDurationFd10msFd15msFd20msFd30msFd32msr"   re   r   r$   r&   rg   r   r   <module>rx      sG   0  	  , 
"
"
+
+##--##--##--##--##--  	!!((!!((!!((!!((!!(( +# +(43 4.xP xPI  ,FLL;qc"#FLLWX
&qc*
++,s   D   E%2EE