3
uQh                 @   sV   d dl Z d dlZd dlZd dlZddlmZ ddlmZ ddlm	Z	 G dd dZ
dS )    N   )	TLRequest)MessageContainer)	TLMessagec               @   s0   e Zd ZdZdd Zdd Zdd Zdd	 Zd
S )MessagePackeraN  
    This class packs `RequestState` as outgoing `TLMessages`.

    The purpose of this class is to support putting N `RequestState` into a
    queue, and then awaiting for "packed" `TLMessage` in the other end. The
    simplest case would be ``State -> TLMessage`` (1-to-1 relationship) but
    for efficiency purposes it's ``States -> Container`` (N-to-1).

    This addresses several needs: outgoing messages will be smaller, so the
    encryption and network overhead also is smaller. It's also a central
    point where outgoing requests are put, and where ready-messages are get.
    c             C   s(   || _ tj | _tj | _|t | _d S )N)	_statecollectionsdeque_dequeasyncioEvent_ready__name___log)selfstateloggers r   E/tmp/pip-build-2nz6shyl/telethon/telethon/extensions/messagepacker.py__init__   s    

zMessagePacker.__init__c             C   s   | j j| | jj  d S )N)r
   appendr   set)r   r   r   r   r   r      s    zMessagePacker.appendc             C   s   | j j| | jj  d S )N)r
   extendr   r   )r   Zstatesr   r   r   r   #   s    zMessagePacker.extendc                s  | j s | jj  | jj I dH  tj }g }d}x| j oDt|tjkr| j j	 }|t|j
tj 7 }|tjkr| jj||j
t|jt|jr|jjndd|_|j| | jjd|j|jjjt|j q2|r| j j| P | jjd|jjjt|j
 |jjtd d}q2q2W |sdS t|dkrvt j!dtj"t||j#  }tj }| jj||d	d
}x|D ]}||_$qfW |j# }||fS )z
        Returns (batch, data) if one or more items could be retrieved.

        If the cancellation occurs or only invalid items were in the
        queue, (None, None) will be returned instead.
        Nr   )Zafter_idzAssigned msg_id = %d to %s (%x)z:Message payload for %s is too long (%d) and cannot be sentzRequest payload is too big   z<IiF)Zcontent_related)NN)%r
   r   clearwaitioBytesIOlenr   ZMAXIMUM_LENGTHpopleftdatar   ZSIZE_OVERHEADZMAXIMUM_SIZEr   Zwrite_data_as_message
isinstancerequestr   afterZmsg_idr   r   debug	__class__r   id
appendleftwarningfutureZset_exception
ValueErrorstructpackZCONSTRUCTOR_IDgetvaluecontainer_id)r   bufferbatchsizer   r    r.   sr   r   r   get'   sR    






zMessagePacker.getN)r   
__module____qualname____doc__r   r   r   r3   r   r   r   r   r      s
   r   )r   r   r   r+   tlr   Ztl.core.messagecontainerr   Ztl.core.tlmessager   r   r   r   r   r   <module>   s   