o
    if                     @   s`   d dl Z d dlmZmZmZ d dlmZ d dlmZ d dl	m
Z
 G dd dZG dd	 d	ZdS )
    N)OptionalCallable	Awaitable)	WebSocket)WebSocketDisconnect)Logc                   @   s,   e Zd ZdZdd Zd
ddZd
dd	ZdS )ConnectionStateay  
    Tracks the current Mcube call session and manages connection state.
    
    - Holds the current stream ID and call ID for the active Mcube call session.
    - Provides methods to reset or clear state when a new call starts or an interruption occurs.
    
    Audio-related state is now managed by AudioService, so this class focuses only on connection/session state.
    c                 C   s   d | _ d | _d S N)	stream_idcall_idself r   @/var/www/html/live_calls/homebook/services/connection_manager.py__init__   s   
zConnectionState.__init__returnNc                 C      dS )z%Reset state when a new stream starts.Nr   r   r   r   r   reset_stream_state      z"ConnectionState.reset_stream_statec                 C   r   )z2Clear response-related state during interruptions.Nr   r   r   r   r   clear_response_state   r   z$ConnectionState.clear_response_stater   N)__name__
__module____qualname____doc__r   r   r   r   r   r   r   r   	   s
    	
r   c                	   @   s   e Zd ZdZdefddZdeddfdd	Zd
eege	d f deege	d f dee
ge	d f ddfddZde
ddfddZdddZddedee
 ddfddZdS )WebSocketConnectionManagera  
    Orchestrates WebSocket communication between Mcube and ElevenLabs for Service Type 4.
    
    - Establishes, maintains, and closes WebSocket connections to Mcube (FastAPI).
    - Routes incoming messages to appropriate event handlers for media, start, and playedStream events.
    - Sends and receives messages, manages connection state, and coordinates with AudioService for checkpoint/clear events.
    
    This is the main interface for real-time, bidirectional communication between Mcube and ElevenLabs.
    mcube_wsc                 C   s   || _ t | _d S r	   )r   r   state)r   r   r   r   r   r   -   s   z#WebSocketConnectionManager.__init__messager   Nc              
      s   z| j jjdkrW dS | j |I dH  W dS  tyb } z?t| }d|v s1d|v s1d|v r2n%ddl}t	d|  t	d|  t	d	|
   W Y d}~dS W Y d}~dS d}~ww )
z"Send a message to Mcube WebSocket.	CONNECTEDNnot connectedclosedacceptr   u'   ⚠️ Error sending message to Mcube: z	Message: zFull traceback: )r   client_statename	send_json	Exceptionstrlower	tracebackr   warning
format_exc)r   r   e	error_strr)   r   r   r   send_to_mcube1   s    "z(WebSocketConnectionManager.send_to_mcubeon_mediaon_starton_played_streamc              
      s  z| j jjdkrW dS | j  2 z3 dH W }| j jjdkr" W dS t|}|d dkr5||I dH  q|d dkr|di }|d}|d}|| j_|| j_	|r_t
d||d	 nzt
d
| W n tyu   t
d Y nw | j  ||I dH  q|d dkr|d}	|	r||	I dH  q6 W dS  ty   t
d Y dS  ty }
 z)t|
 }d|v sd|v sd|v rnt
d|
  W Y d}
~
dS W Y d}
~
dS d}
~
ww )a&  
        Receive messages from Mcube and route them to appropriate handlers.
        
        Args:
            on_media: Handler for media events
            on_start: Handler for call start events (now receives full data)
            on_played_stream: Handler for playedStream events
        r   NeventmediastartstreamIdcallIdzMcube Start)r5   r6   zMcube Start (no callId)zCMcube start payload (no callId) and failed to serialize start_info.playedStreamr$   z'Mcube WebSocket disconnected (expected)r    r"   r!   zError in receive_from_mcube: )r   r#   r$   	iter_textjsonloadsgetr   r
   r   r   r2   r&   errorr   r   infor'   r(   )r   r/   r0   r1   r   data
start_infor
   r   r$   r,   r-   r   r   r   receive_from_mcubeD   sX   





$z-WebSocketConnectionManager.receive_from_mcuber$   c                    sD   | j jr ddlm} | }|| j j|}| |I dH  dS dS )z4Send a checkpoint event to Mcube using AudioService.r   AudioServiceN)r   r
   services.audio_servicerB   create_checkpoint_messager.   )r   r$   rB   audio_servicecheckpoint_eventr   r   r   send_checkpoint_to_mcube   s   z3WebSocketConnectionManager.send_checkpoint_to_mcubec                    sB   | j jrddlm} | }|| j j}| |I dH  dS dS )z/Clear audio buffer in Mcube using AudioService.r   rA   N)r   r
   rC   rB   create_clear_messager.   )r   rB   rE   clear_eventr   r   r   clear_mcube_audio   s   z,WebSocketConnectionManager.clear_mcube_audio  codereasonc              
      sd   z| j j||p	ddI dH  td W dS  ty1 } ztd|  W Y d}~dS d}~ww )zeClose the Mcube WebSocket connection gracefully.
        This ends the call on Mcube's side.
        znormal closure)rL   rM   Nz!Closed Mcube WebSocket connectionz!Failed to close Mcube WebSocket: )r   closer   r=   r&   r<   )r   rL   rM   r,   r   r   r   close_mcube_connection   s   z1WebSocketConnectionManager.close_mcube_connectionr   )rK   N)r   r   r   r   r   r   dictr.   r   r   r'   r@   rG   rJ   intr   rO   r   r   r   r   r   "   s     

B
	 	r   )r9   typingr   r   r   fastapir   fastapi.websocketsr   services.log_utilsr   r   r   r   r   r   r   <module>   s    