a
    ’éio  ã                   @   sR  d Z ddgZddlZddlZddlZz"ddlZejejejej	dœZ
W n ey\   dZY n0 ddlmZmZ ddlmZ ddlmZmZmZmZmZ d	d
lmZmZmZmZmZmZ d	dlmZm Z m!Z!m"Z" ddl#m$Z$m%Z% e&e'dœdd„Z(G dd„ deƒZ)G dd„ de)ƒZ*G dd„ de*ƒZ+G dd„ deƒZ,G dd„ de,ƒZ-G dd„ de,ƒZ.dS )zFModule implementing low-level socket communication with MySQL servers.ÚMySQLTcpSocketÚMySQLUnixSocketé    N)ÚTLSv1úTLSv1.1úTLSv1.2úTLSv1.3)ÚABCÚabstractmethod)Údeque)ÚAnyÚDequeÚListÚOptionalÚTupleé   )ÚInterfaceErrorÚNotSupportedErrorÚOperationalErrorÚProgrammingErrorÚReadTimeoutErrorÚWriteTimeoutError)ÚCOMPRESSED_PACKET_HEADER_LENGTHÚMAX_PAYLOAD_LENGTHÚMIN_COMPRESS_LENGTHÚPACKET_HEADER_LENGTHé   )ÚStreamWriterÚopen_connection)ÚerrÚreturnc                 C   s    | j st| ƒS | j › d| j› �S )z`Reformat the IOError error message.

    This function reformats the IOError error message.
    ú )ÚerrnoÚstrÚstrerror)r   © r$   úK/home/Claro/venv/lib/python3.9/site-packages/mysql/connector/aio/network.pyÚ_strioerrorI   s    r&   c                
   @   s\   e Zd ZdZed	eeeee	 ee	 ee	 ddœdd„ƒZ
ed
ejeee	 edœdd„ƒZdS )ÚNetworkBrokeraP  Broker class interface.

    The network object is a broker used as a delegate by a socket object. Whenever the
    socket wants to deliver or get packets to or from the MySQL server it needs to rely
    on its network broker (netbroker).

    The netbroker sends `payloads` and receives `packets`.

    A packet is a bytes sequence, it has a header and body (referred to as payload).
    The first `PACKET_HEADER_LENGTH` or `COMPRESSED_PACKET_HEADER_LENGTH`
    (as appropriate) bytes correspond to the `header`, the remaining ones represent the
    `payload`.

    The maximum payload length allowed to be sent per packet to the server is
    `MAX_PAYLOAD_LENGTH`. When  `send` is called with a payload whose length is greater
    than `MAX_PAYLOAD_LENGTH` the netbroker breaks it down into packets, so the caller
    of `send` can provide payloads of arbitrary length.

    Finally, data received by the netbroker comes directly from the server, expect to
    get a packet for each call to `recv`. The received packet contains a header and
    payload, the latter respecting `MAX_PAYLOAD_LENGTH`.
    N©ÚwriterÚaddressÚpayloadÚpacket_numberÚcompressed_packet_numberÚwrite_timeoutr   c                 Ã   s   dS )a™  Send `payload` to the MySQL server.

        If provided a payload whose length is greater than `MAX_PAYLOAD_LENGTH`, it is
        broken down into packets.

        Args:
            sock: Object holding the socket connection.
            address: Socket's location.
            payload: Packet's body to send.
            packet_number: Sequence id (packet ID) to attach to the header when sending
                           plain packets.
            compressed_packet_number: Same as `packet_number` but used when sending
                                      compressed packets.
            write_timeout: Timeout in seconds before which sending a packet to the server
                           should finish else WriteTimeoutError is raised.


        Raises:
            :class:`OperationalError`: If something goes wrong while sending packets to
                                       the MySQL server.
        Nr$   )Úselfr)   r*   r+   r,   r-   r.   r$   r$   r%   Úwritei   s    
zNetworkBroker.write©Úreaderr*   Úread_timeoutr   c                 Ã   s   dS )aM  Get the next available packet from the MySQL server.

        Args:
            sock: Object holding the socket connection.
            address: Socket's location.
            read_timeout: Timeout in seconds before which reading a packet from the server
                          should finish.

        Returns:
            packet: A packet from the MySQL server.

        Raises:
            :class:`OperationalError`: If something goes wrong while receiving packets
                                       from the MySQL server.
            :class:`ReadTimeoutError`: If the time to receive a packet from the server takes
                                       longer than `read_timeout`.
            :class:`InterfaceError`: If something goes wrong while receiving packets
                                     from the MySQL server.
        Nr$   )r/   r2   r*   r3   r$   r$   r%   Úread‰   s    zNetworkBroker.read)NNN)N)Ú__name__Ú
__module__Ú__qualname__Ú__doc__r	   r   r"   Úbytesr   Úintr0   ÚasyncioÚStreamReaderÚ	bytearrayr4   r$   r$   r$   r%   r'   Q   s,      ùø üûr'   c                	   @   sÄ   e Zd ZdZddœdd„Zeeeeef dœdd„ƒZ	de
e dd	œd
d„Zeeeddœdd„Zdejee
e edœdd„Zdeeee
e e
e e
e ddœdd„Zdejee
e edœdd„ZdS )ÚNetworkBrokerPlainú,Broker class for MySQL socket communication.N©r   c                 C   s
   d| _ d S ©Néÿÿÿÿ©Ú_pktnr©r/   r$   r$   r%   Ú__init__¨   s    zNetworkBrokerPlain.__init__©Úpktr   c                 C   sB   t | ƒtk rtdƒ‚t d| dd… d ¡d | d  }}||fS )ú-Recover the header information from a packet.ú3Can't recover header info from an incomplete packetú<Ir   é   ó    )Úlenr   Ú
ValueErrorÚstructÚunpack)rH   ÚpllÚseqidr$   r$   r%   Ú
get_header«   s    þzNetworkBrokerPlain.get_header©Únext_idr   c                 C   s0   |du r|  j d7  _ n|| _ |  j d;  _ dS ©z:Set the given packet id, if any, else increment packet id.Nr   é   rC   ©r/   rV   r$   r$   r%   Ú_set_next_pktnr¸   s    z"NetworkBrokerPlain._set_next_pktnr©r)   r*   rH   r   c              
   Ã   sŠ   z|  |¡ | ¡ I dH  W nh tyV } z"td|t|ƒfd�|‚W Y d}~n8d}~0  ty„ } ztdd�|‚W Y d}~n
d}~0 0 dS )z!Write packet to the comm channel.Né  ©r!   ÚvaluesiÖ  ©r!   )r0   ZdrainÚIOErrorr   r&   ÚAttributeError)r/   r)   r*   rH   r   r$   r$   r%   Ú
_write_pktÀ   s    
ÿþzNetworkBrokerPlain._write_pktr   )r2   Úsizer3   r   c              
   Ã   s²   zRt dƒ}t|ƒ|k rNt | |t|ƒ ¡|¡I dH }|sDtdd�‚||7 }q
|W S  tjy„ } ztdd�|‚W Y d}~n2d}~0  tjy¬ } z|‚W Y d}~n
d}~0 0 dS )z(Read `size` bytes from the comm channel.ó    NiÝ  r_   éÐ  )	r=   rN   r;   Úwait_forr4   r   ÚTimeoutErrorr   ÚCancelledError)r/   r2   rc   r3   rH   Úchunkr   r$   r$   r%   Ú_read_chunkÑ   s    ÿ


 zNetworkBrokerPlain._read_chunkr(   c           
      Ã   s"  |   |¡ d}z²tt|ƒt ƒD ]N}t |  ||dt d| j	¡ |||t …  ¡|¡I dH  |   ¡  |t7 }q t |  ||t dt|ƒ| ¡dd… t d| j	¡ ||d…  ¡|¡I dH  W n\ tj
yò }	 ztdd�|	‚W Y d}	~	n4d}	~	0  tj�y }	 z|	‚W Y d}	~	n
d}	~	0 0 dS )	z¤Send payload to the MySQL server.

        If provided a payload whose length is greater than `MAX_PAYLOAD_LENGTH`, it is
        broken down into packets.
        r   ó   ÿÿÿú<BNrK   rL   re   r_   )rZ   ÚrangerN   r   r;   rf   rb   rP   ÚpackrD   rg   r   rh   )
r/   r)   r*   r+   r,   r-   r.   ÚoffsetÚ_r   r$   r$   r%   r0   ç   sD    
ÿþýø


ÿ
þýø
 zNetworkBrokerPlain.writer1   c              
   Ã   s~   z>|   |t|¡I dH }|  |¡\}| _||   |||¡I dH  W S  tyx } z"td|t|ƒfd�|‚W Y d}~n
d}~0 0 dS )z+Receive `one` packet from the MySQL server.Nr\   r]   )rj   r   rT   rD   r`   r   r&   )r/   r2   r*   r3   ÚheaderZpayload_lenr   r$   r$   r%   r4     s    ÿþzNetworkBrokerPlain.read)N)r   N)NNN)N)r5   r6   r7   r8   rF   Ústaticmethodr9   r   r:   rT   r   rZ   r   r"   rb   r;   r<   r=   rj   r0   r4   r$   r$   r$   r%   r>   ¥   sJ   
û  üû   ùø5 üûr>   c                	       sø   e Zd ZdZddœ‡ fdd„Zeeeee dœdd„ƒZ	eee
eeef d	œd
d„ƒZdee ddœdd„Zeeeddœ‡ fdd„Zdeeeee ee ee ddœ‡ fdd„Zdejeee ddœ‡ fdd„Zdejeee edœ‡ fdd„Z‡  ZS )ÚNetworkBrokerCompressedr?   Nr@   c                    s   t ƒ  ¡  d| _tƒ | _d S rA   )ÚsuperrF   Ú_compressed_pktnrr
   Ú_queue_readrE   ©Ú	__class__r$   r%   rF   1  s    
z NetworkBrokerCompressed.__init__)r+   Úpktnrr   c                 C   s–   d}g }t t| ƒt ƒD ]>}| dt d|¡ | ||t …  ¡ |d d }|t7 }q| t dt| ƒ| ¡dd… t d|¡ | |d…  ¡ |S )	z2Prepare a payload for sending to the MySQL server.r   rk   rl   r   rX   rK   rL   N)rm   rN   r   ÚappendrP   rn   )r+   ry   ro   Zpktsrp   r$   r$   r%   Ú_prepare_packets6  s(    
ÿþÿ

ÿ
þÿz(NetworkBrokerCompressed._prepare_packetsrG   c                 C   sb   t | ƒtk rtdƒ‚t d| dd… d ¡d | d t d| dd… d ¡d   }}}|||fS )rI   rJ   rK   r   rL   rM   é   é   )rN   r   rO   rP   rQ   )rH   Úcompressed_pllrS   Úuncompressed_pllr$   r$   r%   rT   O  s    ý
z"NetworkBrokerCompressed.get_headerrU   c                 C   s0   |du r|  j d7  _ n|| _ |  j d;  _ dS rW   )ru   rY   r$   r$   r%   Ú_set_next_compressed_pktnr]  s    z2NetworkBrokerCompressed._set_next_compressed_pktnrr[   c                 ƒ   sb   t  |¡}t dt|ƒ¡dd… t d| j¡ t dt|ƒ¡dd…  | }tƒ  |||¡I dH S )z1Compress packet and write it to the comm channel.rK   r   rL   rl   N)ÚzlibÚcompressrP   rn   rN   ru   rt   rb   )r/   r)   r*   rH   Úcompressed_pktrw   r$   r%   rb   e  s    
ÿþýÿz"NetworkBrokerCompressed._write_pktr(   c                 ƒ   s|  |   |¡ |  |¡ �z&tdƒ |  || j¡¡}t|ƒtt kr¸d}t	t|ƒt ƒD ]<}	t
 |  |||||t … ¡|¡I dH  |  ¡  |t7 }qTt
 |  ||||d… ¡|¡I dH  n‚t|ƒtkrât
 |  |||¡|¡I dH  nXt
 tƒ  ||t dt|ƒ¡dd… t d| j¡ t dd¡dd…  | ¡|¡I dH  W n: t
jt
jf�yv }
 ztdd�|
‚W Y d}
~
n
d}
~
0 0 dS )	z¼Send `payload` as compressed packets to the MySQL server.

        If provided a payload whose length is greater than `MAX_PAYLOAD_LENGTH`, it is
        broken down into packets.
        rd   r   NrK   rL   rl   re   r_   )rZ   r€   r=   Újoinr{   rD   rN   r   r   rm   r;   rf   rb   r   rt   rP   rn   ru   rh   rg   r   )r/   r)   r*   r+   r,   r-   r.   Zpayload_prepro   rp   r   rw   r$   r%   r0   u  sV    

ÿýú

þ	ÿÿþýý÷zNetworkBrokerCompressed.write)r2   r~   r3   r   c           
      ƒ   sî   t t tƒ  |||¡I dH ¡ƒ}d}|t|ƒk rêt d|||t d … d ¡d }t| t|ƒ| krÀtƒ  |t	|¡I dH }|  
|¡\}| _}tƒ  |||¡I dH }	||dkr´|	nt |	¡7 }| j |||t | … ¡ |t| 7 }q$dS )z&Handle reading of a compressed packet.Nr   rK   r   rM   )r=   r�   Ú
decompressrt   rj   rN   rP   rQ   r   r   rT   ru   rv   rz   )
r/   r2   r~   r3   rH   ro   rR   rq   r   rƒ   rw   r$   r%   Ú_read_compressed_pkt¾  s>    ÿÿÿþÿ
	üÿ
ÿýz,NetworkBrokerCompressed._read_compressed_pktr1   c           	   
   ƒ   sÌ   | j sªzhtƒ  |t|¡I dH }|  |¡\}| _}|dkrX| j  tƒ  |||¡I dH ¡ n|  |||¡I dH  W n: ty¨ } z"t	d|t
|ƒfd�|‚W Y d}~n
d}~0 0 | j s´dS | j  ¡ }|d | _|S )z{Receive `one` or `several` packets from the MySQL server, enqueue them, and
        return the packet at the head.
        Nr   r\   r]   rL   )rv   rt   rj   r   rT   ru   rz   r†   r`   r   r&   ÚpopleftrD   )	r/   r2   r*   r3   rq   r~   r   r   rH   rw   r$   r%   r4   í  s8    
ÿ
	üÿÿÿþ

zNetworkBrokerCompressed.read)N)NNN)N)N)r5   r6   r7   r8   rF   rr   r9   r:   r   r{   r   rT   r   r€   r   r"   rb   r0   r;   r<   r†   r=   r4   Ú__classcell__r$   r$   rw   r%   rs   .  sL   
û   ùøM üû3 üûrs   c                
   @   s  e Zd ZdZddœdd„Zeedœdd„ƒZee	ddœd	d
„ƒZ
ddœdd„Zedœdd„Zeddœdd„Zddœdd„Zejddœdd„Zd!eee ee ee ddœdd„Zd"ee edœdd„Zdddddg g fee ee ee ee ee eee  eee  ejdœdd „ZdS )#ÚMySQLSocketz�MySQL socket communication interface.

    Examples:
        Subclasses: network.MySQLTCPSocket and network.MySQLUnixSocket.
    Nr@   c                 C   s*   d| _ d| _d| _d| _tƒ | _d| _dS )zsNetwork layer where transactions are made with plain (uncompressed) packets
        is enabled by default.
        NF)Ú_readerÚ_writerÚ_connection_timeoutÚ_addressr>   Ú
_netbrokerÚ_is_connectedrE   r$   r$   r%   rF   $  s    zMySQLSocket.__init__c                 C   s   | j S )zSocket location.)r�   rE   r$   r$   r%   r*   /  s    zMySQLSocket.address©Úkwargsr   c                 Ë   s   dS )zOpen the socket.Nr$   ©r/   r‘   r$   r$   r%   r   4  s    zMySQLSocket.open_connectionc              
   Ã   sl   | j rbz6| j  ¡  | j jdur*| j j ¡  | j  ¡ I dH  W n$ ty` } zW Y d}~n
d}~0 0 d| _dS )zClose the connection.NF)r‹   ÚcloseÚ	transportÚabortZwait_closedÚ	Exceptionr�   )r/   rp   r$   r$   r%   Úclose_connection8  s    
zMySQLSocket.close_connectionc                 C   s   | j S )zˆCheck if the socket is connected.

        Return:
            bool: Returns `True` if the socket is connected to MySQL server.
        )r�   rE   r$   r$   r%   Úis_connectedG  s    zMySQLSocket.is_connected)Útimeoutr   c                 C   s
   || _ dS )zSet the connection timeout.N)rŒ   )r/   r™   r$   r$   r%   Úset_connection_timeoutO  s    z"MySQLSocket.set_connection_timeoutc                 C   s   t ƒ | _dS )zIEnable network layer where transactions are made with compressed packets.N)rs   rŽ   rE   r$   r$   r%   Úswitch_to_compressed_modeS  s    z%MySQLSocket.switch_to_compressed_mode)Ússl_contextr   c                 Ã   sD   | j dusJ ‚| j j d¡}|jdkr.tdƒ‚| j  |¡I dH  dS )a?  Upgrade an existing stream-based connection to TLS.

        The `start_tls()` method from `asyncio.streams.StreamWriter` is only available
        in Python 3.11. This method is used as a workaround.

        The MySQL TLS negotiation happens in the middle of the TCP connection.
        Therefore, passing a socket to open connection will cause it to negotiate
        TLS on an existing connection.

        Args:
            ssl_context: The SSL Context to be used.

        Raises:
            RuntimeError: If the transport does not expose the socket instance.
        NÚsocketr   z,SSL is not supported when using Unix sockets)r‹   r”   Zget_extra_infoÚfamilyr   Z	start_tls)r/   rœ   r�   r$   r$   r%   Úswitch_to_sslW  s
    
zMySQLSocket.switch_to_ssl)r+   r,   r-   r.   r   c                 Ã   s&   | j j| j| j||||d�I dH  dS )z!Send packets to the MySQL server.)r,   r-   r.   N)rŽ   r0   r‹   r*   )r/   r+   r,   r-   r.   r$   r$   r%   r0   p  s    úzMySQLSocket.write)r3   r   c                 Ã   s   | j  | j| j|¡I dH S )z#Read packets from the MySQL server.N)rŽ   r4   rŠ   r*   )r/   r3   r$   r$   r%   r4   �  s    zMySQLSocket.readF)Ússl_caÚssl_certÚssl_keyÚssl_verify_certÚssl_verify_identityÚtls_versionsÚtls_cipher_suitesr   c                 C   s  d}| j stdd�‚tdu r$tdƒ‚�z‚|r¤|jdd� |d }t| }	t |	¡}
|dkr¬d	|vrr|
 jtjO  _d
|vrŠ|
 jtj	O  _d|vr¬|
 jtj
O  _nt ¡ }
||
_|rÀtj|
_n|rÎtj|
_ntj|
_|
 ¡  |�r0z|
 |¡ W n< ttjf�y. } ztd|› �ƒ|‚W Y d}~n
d}~0 0 |�r„z|
 ||¡ W n< ttjf�y‚ } ztd|› �ƒ|‚W Y d}~n
d}~0 0 |�r¤|d	k�r¤|
 d |¡¡ |
W S  t�yØ } ztdƒ|‚W Y d}~nHd}~0  tttjtjf�y } ztt|ƒƒ|‚W Y d}~n
d}~0 0 dS )zBuild a SSLContext.Ni   r_   z&Python installation has no SSL supportT)Úreverser   r   r   r   r   zInvalid CA Certificate: zInvalid Certificate/Key: ú:)rŠ   r   ÚsslÚRuntimeErrorÚsortÚTLS_VERSIONSÚ
SSLContextÚoptionsÚOP_NO_TLSv1_2ÚOP_NO_TLSv1_1ÚOP_NO_TLSv1Úcreate_default_contextÚcheck_hostnameÚCERT_REQUIREDÚverify_modeÚCERT_OPTIONALÚ	CERT_NONEÚload_default_certsÚload_verify_locationsr`   ÚSSLErrorÚload_cert_chainÚset_ciphersr„   Ú	NameErrorr   ÚNotImplementedErrorÚCertificateErrorr"   )r/   r    r¡   r¢   r£   r¤   r¥   r¦   Ztls_versionZssl_protocolÚcontextr   r$   r$   r%   Úbuild_ssl_context…  s`    



&&üzMySQLSocket.build_ssl_context)NNN)N)r5   r6   r7   r8   rF   Úpropertyr"   r*   r	   r   r   r—   Úboolr˜   r:   rš   r›   r©   r­   rŸ   r9   r   r0   r=   r4   r   rÁ   r$   r$   r$   r%   r‰     sN      ûúø

÷r‰   c                       s<   e Zd ZdZdeeedœ‡ fdd„Zedd	œd
d„Z	‡  Z
S )r   z�MySQL socket class using TCP/IP.

    Args:
        host: MySQL host name.
        port: MySQL port.
        force_ipv6: Force IPv6 usage.
    ú	127.0.0.1éê  F)ÚhostÚportÚ
force_ipv6c                    s0   t ƒ  ¡  || _|| _|| _|› d|› �| _d S )Nr¨   )rt   rF   Ú_hostÚ_portZ_force_ipv6r�   )r/   rÆ   rÇ   rÈ   rw   r$   r%   rF   Ù  s
    
zMySQLTcpSocket.__init__Nr�   c                 Ë   s0   t f | j| jdœ|¤ŽI dH \| _| _d| _dS )zOpen TCP/IP connection.)rÆ   rÇ   NT)r   rÉ   rÊ   rŠ   r‹   r�   r’   r$   r$   r%   r   â  s    ÿÿzMySQLTcpSocket.open_connection)rÄ   rÅ   F)r5   r6   r7   r8   r"   r:   rÃ   rF   r   r   rˆ   r$   r$   rw   r%   r   Ð  s   	 ÿÿ	c                       s8   e Zd ZdZd
edœ‡ fdd„Zeddœdd	„Z‡  ZS )r   zbMySQL socket class using UNIX sockets.

    Args:
        unix_socket: UNIX socket file path.
    ú/tmp/mysql.sock)Úunix_socketc                    s   t ƒ  ¡  || _d S )N)rt   rF   r�   )r/   rÌ   rw   r$   r%   rF   ñ  s    
zMySQLUnixSocket.__init__Nr�   c                 Ë   s.   t jf d| ji|¤ŽI dH \| _| _d| _dS )zOpen UNIX socket connection.ÚpathNT)r;   Zopen_unix_connectionr�   rŠ   r‹   r�   r’   r$   r$   r%   r   õ  s    ÿÿ
ýzMySQLUnixSocket.open_connection)rË   )	r5   r6   r7   r8   r"   rF   r   r   rˆ   r$   r$   rw   r%   r   ê  s   )/r8   Ú__all__r;   rP   r�   r©   ÚPROTOCOL_TLSv1ÚPROTOCOL_TLSv1_1ÚPROTOCOL_TLSv1_2ÚPROTOCOL_TLSr¬   ÚImportErrorÚabcr   r	   Úcollectionsr
   Útypingr   r   r   r   r   Úerrorsr   r   r   r   r   r   Únetworkr   r   r   r   Úutilsr   r   r`   r"   r&   r'   r>   rs   r‰   r   r   r$   r$   r$   r%   Ú<module>   s:   ü

 T 
 p 4