§
    5Ï½j~  ã                  ó¨   — d Z ddlmZ ddlZddlZddlmZmZmZ ddl	m
Z
 ddlmZmZ ddlmZmZmZmZmZmZ ddlmZ dd	lmZ  G d
„ d¦  «        ZdS )zæ
Main Authoritative Chat Microservice for FreeExile.
Coordinates Two-Tier Moderation, HMAC Item Linking, Channel Policy, and 1M CCU Fan-out Router.
Completely isolated from the 30Hz World Simulation Engine to ensure Zero-Latency.
é    )ÚannotationsN)ÚListÚOptionalÚTuple)ÚChannelManager)ÚChatClusterRouterÚSubscriberCallback)ÚChatChannelTypeÚChatMessageDTOÚItemSnapshotDTOÚQueryItemSnapshotResponseDTOÚSendChatRequestDTOÚSendChatResponseDTO)ÚItemLinkService)ÚChatModerationPipelinec                  óz   — e Zd ZdZ	 	 d+d,d
„Zd-d„Zd.d/d„Zd0d„Zd1d„Zd2d„Z	d3d „Z
d4d!„Zd5d#„Zd6d$„Zd7d%„Zd8d)„Zd*S )9ÚChatServicez‰
    Facade and core orchestration engine for FreeExile's Chat System.
    Decoupled 100% from the 30Hz Zone Server simulation loop.
    ó!   FREEEXILE_SECRET_SIGNING_KEY_2026é@   Úitem_secret_keyÚbytesÚcluster_shardsÚintÚreturnÚNonec                ó¦   — t          ¦   «         | _        t          |¬¦  «        | _        t	          ¦   «         | _        t          |¬¦  «        | _        d S )N)Úsecret_signing_key)Ú
num_shards)r   Ú	moderatorr   Úitem_link_servicer   Úchannel_managerr   Úcluster_router)Úselfr   r   s      ú1C:\Projects\FreeExile\server\chat\chat_service.pyÚ__init__zChatService.__init__!   sK   € õ
 0Ñ1Ô1ˆŒÝ!0ÀOÐ!TÑ!TÔ!TˆÔÝ-Ñ/Ô/ˆÔÝ/¸>ÐJÑJÔJˆÔÐÐó    Úrequestr   r   c              ƒ  óú  K  — | j                              |¦  «        \  }}}|st          d||¬¦  «        S | j                             |j        ¦  «        }|j        r8| j                              |j        d¬¦  «         t          dd|j	        ¬¦  «        S g }|j
        D ]=}| j        j                             |¦  «        }|r|\  }	}
|                     |	¦  «         Œ>dt          t!          j        ¦   «         dz  ¦  «        › d	t#          j        ¦   «         j        d
d…         › �}t          t!          j        ¦   «         dz  ¦  «        }t)          di d|“d|j        “d|j        “d|j        “d|j        “d|j        “d|j        “d|j        “d|j        “d|“d|j        “d|j	        “dt9          |¦  «        “d|j        “d|j        “d|j        “Ž}| j                               |¦  «         | j          !                    |j        |j        |j        |j        |j        |j        ¬¦  «        }| j          "                    ||¦  «         | j#         $                    ||¦  «        ƒ d
{V —† t          d||j        |j	        ¬¦  «        S ) aK  
        Processes an incoming chat message request end-to-end:
        1. Channel permission, rate limit, and persistent mute verification.
        2. Two-tier content moderation and Anti-RMT risk scoring.
        3. Linked items verification (HMAC check).
        4. Broadcast to cluster subscribers via sharded fan-out.
        F)ÚsuccessÚerror_messageÚcooldown_remaining_msç      œ@)Úduration_secondsui   TÃ i khoáº£n bá»‹ táº¡m khÃ³a chat do vi pháº¡m chÃ­nh sÃ¡ch an ninh (RMT / Lá»«a Ä‘áº£o / Quáº£ng cÃ¡o)!)r)   r*   Ú
risk_scoreÚmsg_iè  Ú_Né   Ú
message_idÚ	sender_idÚsender_nameÚsender_titleÚsender_guild_tagÚchannelÚ	target_idÚraw_contentÚfiltered_contentÚtimestamp_msÚis_censoredÚmoderation_risk_scoreÚlinked_itemsÚzone_idÚguild_idÚparty_id)r7   r?   r@   rA   Úplayer_aÚplayer_bT)r)   r2   r:   r.   © )%r!   Úvalidate_send_permissionr   r   ÚprocessÚcontentÚshould_auto_muteÚmute_playerr3   r.   Úlink_item_uuidsr    Ú_snapshot_cacheÚgetÚappendr   ÚtimeÚuuidÚuuid4Úhexr   r4   r5   r6   r7   r8   r:   r<   Útupler?   r@   rA   Úrecord_message_sentÚget_channel_keyÚadd_to_historyr"   Úbroadcast_to_channel)r#   r'   ÚallowedÚerror_reasonÚcooldown_msÚ
mod_resultÚlinked_snapshotsÚitem_uuid_strÚ
snap_entryÚsnapshotr0   Úmsg_idÚnow_msÚmessageÚchannel_keys                  r$   Úhandle_send_chatzChatService.handle_send_chat+   s7  è è € ð .2Ô-A×-ZÒ-ZÐ[bÑ-cÔ-cÑ*ˆ�˜{Øð 	Ý&ØØ*Ø&1ðñ ô ð ð ”^×+Ò+¨G¬OÑ<Ô<ˆ
ØÔ&ð 	àÔ ×,Ò,¨WÔ->ÐQWÐ,ÑXÔXÐXÝ&Øð JØ%Ô0ðñ ô ð ð 35ÐØ$Ô4ð 	2ð 	2ˆMØÔ/Ô?×CÒCÀMÑRÔRˆJØð 2Ø(‘�˜!Ø ×'Ò'¨Ñ1Ô1Ð1øð I��DœI™KœK¨$Ñ.Ñ/Ô/ÐHÐHµ$´*±,´,Ô2BÀ2ÀAÀ2Ô2FÐHÐHˆÝ•T”Y‘[”[ 4Ñ'Ñ(Ô(ˆå ð 
ð 
ð 
Ø�vð
àÔ'Ð'ð
ð  Ô+Ð+ð
ð !Ô-Ð-ð	
ð
 %Ô5Ð5ð
ð ”O�Oð
ð Ô'Ð'ð
ð  œ˜ð
ð (Ô8Ð8ð
ð  ˜ð
ð #Ô.Ð.ð
ð #-Ô"7Ð"7ð
õ Ð/Ñ0Ô0Ð0ð
ð ”O�Oð
ð Ô%Ð%ð
ð  Ô%Ð%ð!
ˆð( 	Ô×0Ò0°Ñ9Ô9Ð9ØÔ*×:Ò:Ø”OØ”OØÔ%ØÔ%ØÔ&ØÔ&ð ;ñ 
ô 
ˆð 	Ô×+Ò+¨K¸ÑAÔAÐAð Ô!×6Ò6°{ÀGÑLÔLÐLÐLÐLÐLÐLÐLÐLå"ØØØ'Ô8Ø!Ô,ð	
ñ 
ô 
ð 	
r&   r,   Ú	player_idr-   Úfloatc                ó<   — | j                              ||¦  «         dS )z3Applies a persistent mute lock on a player account.N)r!   rI   )r#   rd   r-   s      r$   rI   zChatService.mute_player|   s"   € àÔ×(Ò(¨Ð4DÑEÔEÐEÐEÐEr&   c                ó:   — | j                              |¦  «         dS )z4Lifts a chat mute restriction from a player account.N)r!   Úunmute_player©r#   rd   s     r$   rh   zChatService.unmute_player€   s   € àÔ×*Ò*¨9Ñ5Ô5Ð5Ð5Ð5r&   úTuple[bool, int]c                ó6   — | j                              |¦  «        S )zOChecks if a player is currently muted, returning (is_muted, remaining_seconds).)r!   Úis_player_mutedri   s     r$   rl   zChatService.is_player_muted„   s   € àÔ#×3Ò3°IÑ>Ô>Ð>r&   Ú	item_uuidÚstrÚclaimed_signaturer   c                ó8   — | j                              ||¦  «        S )z;Retrieves and cryptographically validates an item snapshot.)r    Úquery_item_snapshot)r#   rm   ro   s      r$   rq   zChatService.query_item_snapshotˆ   s   € àÔ%×9Ò9¸)ÐEVÑWÔWÐWr&   rb   Ú	client_idÚcallbackr	   c                óH   — | j         j                             |||¦  «         dS )z6Subscribes a client socket / session to a channel key.N)r"   ÚregistryÚ	subscribe)r#   rb   rr   rs   s       r$   Úsubscribe_clientzChatService.subscribe_clientŒ   s&   € àÔÔ$×.Ò.¨{¸IÀxÑPÔPÐPÐPÐPr&   c                óF   — | j         j                             ||¦  «         dS )z:Unsubscribes a client socket / session from a channel key.N)r"   ru   Úunsubscribe)r#   rb   rr   s      r$   Úunsubscribe_clientzChatService.unsubscribe_client�   s$   € àÔÔ$×0Ò0°¸iÑHÔHÐHÐHÐHr&   úList[ChatMessageDTO]c                ó6   — | j                              |¦  «        S )z/Fetches recent buffered messages for a channel.)r!   Úget_history©r#   rb   s     r$   Úget_channel_historyzChatService.get_channel_history”   s   € àÔ#×/Ò/°Ñ<Ô<Ð<r&   c                ó:   — | j                              |¦  «         dS )z'Clears buffered messages for a channel.N)r!   Úclear_historyr~   s     r$   Úclear_channel_historyz!ChatService.clear_channel_history˜   s   € àÔ×*Ò*¨;Ñ7Ô7Ð7Ð7Ð7r&   c                ó8   — | j                              ¦   «          dS )z?Resets rate limiting state for testing and cluster maintenance.N)r!   Úreset_rate_limits)r#   s    r$   r„   zChatService.reset_rate_limitsœ   s   € àÔ×.Ò.Ñ0Ô0Ð0Ð0Ð0r&   Úblocked_player_idÚ
is_blockedÚboolc                ó>   — | j                              |||¦  «         dS )z6Manages player blacklists for Whisper spam protection.N)r!   Úset_blacklist_entry)r#   rd   r…   r†   s       r$   r‰   zChatService.set_blacklist_entry    s$   € àÔ×0Ò0°Ð<MÈzÑZÔZÐZÐZÐZr&   N)r   r   )r   r   r   r   r   r   )r'   r   r   r   )r,   )rd   r   r-   re   r   r   )rd   r   r   r   )rd   r   r   rj   )rm   rn   ro   rn   r   r   )rb   rn   rr   r   rs   r	   r   r   )rb   rn   rr   r   r   r   )rb   rn   r   r{   )rb   rn   r   r   )r   r   )rd   r   r…   r   r†   r‡   r   r   )Ú__name__Ú
__module__Ú__qualname__Ú__doc__r%   rc   rI   rh   rl   rq   rw   rz   r   r‚   r„   r‰   rD   r&   r$   r   r      sB  € € € € € ðð ð "FØ ðKð Kð Kð Kð KðO
ð O
ð O
ð O
ðbFð Fð Fð Fð Fð6ð 6ð 6ð 6ð?ð ?ð ?ð ?ðXð Xð Xð XðQð Qð Qð QðIð Ið Ið Ið=ð =ð =ð =ð8ð 8ð 8ð 8ð1ð 1ð 1ð 1ð[ð [ð [ð [ð [ð [r&   r   )r�   Ú
__future__r   rN   rO   Útypingr   r   r   Úserver.chat.channel_managerr   Úserver.chat.chat_cluster_routerr   r	   Úserver.chat.chat_typesr
   r   r   r   r   r   Úserver.chat.item_link_servicer   Úserver.chat.moderationr   r   rD   r&   r$   ú<module>r•      s9  ððð ð #Ð "Ð "Ð "Ð "Ð "à €€€Ø €€€Ø (Ð (Ð (Ð (Ð (Ð (Ð (Ð (Ð (Ð (à 6Ð 6Ð 6Ð 6Ð 6Ð 6Ø QÐ QÐ QÐ QÐ QÐ QÐ QÐ Qðð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð :Ð 9Ð 9Ð 9Ð 9Ð 9Ø 9Ð 9Ð 9Ð 9Ð 9Ð 9ðG[ð G[ð G[ð G[ð G[ñ G[ô G[ð G[ð G[ð G[r&   