
    h2                        d Z ddlZddlZddlZddlZddlmZmZmZ ddl	m
Z
mZmZmZmZ ddlmZ ddlmZ dZd	Z ej(                  d
      Z ej(                  d      Z G d dej.                        Z G d deej2                        Zy)z?
An ``asyncio.Protocol`` subclass for lower level IO handling.
    N)DequeOptionalcast   )SMTPDataErrorSMTPReadTimeoutErrorSMTPResponseExceptionSMTPServerDisconnectedSMTPTimeoutError)SMTPResponse)
SMTPStatus)SMTPProtocoli    s   (?:\r\n|\n|\r(?!\n))s   (?m)^\.c                       e Zd ZdZddeej                     fdZddZddZ	dee
   ddfd	Zdd
Zdej                  ddfdZy)FlowControlMixina  
    Reusable flow control logic for StreamWriter.drain().
    This implements the protocol methods pause_writing(),
    resume_writing() and connection_lost().  If the subclass overrides
    these it must call the super methods.
    StreamWriter.drain() must wait for _drain_helper() coroutine.

    Copied from stdlib as per recommendation: https://bugs.python.org/msg343685.
    Logging and asserts removed, type annotations added.
    Nloopc                     |t        j                         | _        n|| _        d| _        t	        j
                         | _        d| _        y NF)asyncioget_event_loop_loop_pausedcollectionsdeque_drain_waiters_connection_lost)selfr   s     ^/var/www/html/retail-simulation-api/retail/lib/python3.12/site-packages/aiosmtplib/protocol.py__init__zFlowControlMixin.__init__*   s>    < //1DJDJ;F;L;L;N %    returnc                     d| _         y NT)r   r   s    r   pause_writingzFlowControlMixin.pause_writing4   s	    r   c                 x    d| _         | j                  D ]$  }|j                         r|j                  d        & y r   )r   r   done
set_resultr   waiters     r   resume_writingzFlowControlMixin.resume_writing7   s0    ))F;;=!!$' *r   excc                     d| _         | j                  sy | j                  D ]8  }|j                         r||j	                  d        (|j                  |       : y r"   )r   r   r   r&   r'   set_exception)r   r+   r)   s      r   connection_lostz FlowControlMixin.connection_lost>   sN     $||))F;;=;%%d+((- *r   c                 N  K   | j                   rt        d      | j                  sy | j                  j	                         }| j
                  j                  |       	 | d {    | j
                  j                  |       y 7  # | j
                  j                  |       w xY wwNConnection lost)r   ConnectionResetErrorr   r   create_futurer   appendremover(   s     r   _drain_helperzFlowControlMixin._drain_helperK   s       &'899||))+""6*	/LL&&v. &&v.s0   AB%B "B#B 'B%B B""B%streamasyncio.Future[None]c                     t         N)NotImplementedErrorr   r7   s     r   _get_close_waiterz"FlowControlMixin._get_close_waiterW   s    !!r   r:   r    N)__name__
__module____qualname____doc__r   r   AbstractEventLoopr   r$   r*   	Exceptionr.   r6   StreamWriterr=    r   r   r   r      s_    	&Xg&?&?@ &(.8I#6 .4 .
/"(<(< "AW "r   r   c            	           e Zd Z	 ddeej
                     ddf fdZdej                  ddfdZddZ	e
defd	       Zd
ej                  ddfdZdee   ddf fdZdeddfdZdefdZdee   fdZdee   fdZddee   defdZdeddfdZdddedee   defdZ	 ddedee   defdZ	 	 d dej<                  dee   dee   defdZ  xZ!S )!r   Nr   r    c                     t         |   |       d| _        t               | _        d | _        d | _        d | _        | j                  j                         | _
        d| _        y )N)r   F)superr   	_over_ssl	bytearray_buffer_response_waiter	transport_command_lockr   r3   _closed
_quit_sent)r   r   	__class__s     r   r   zSMTPProtocol.__init__\   sW     	d# {HL:>59/3zz/G/G/Ir   r7   r8   c                     | j                   S r:   )rP   r<   s     r   r=   zSMTPProtocol._get_close_waiterj   s    ||r   c                 $    | j                          y r:   )_retrieve_response_exceptionr#   s    r   __del__zSMTPProtocol.__del__m   s     	))+r   c                 j    t        | j                  duxr | j                  j                                S )z<
        Check if our transport is still connected.
        N)boolrN   
is_closingr#   s    r   is_connectedzSMTPProtocol.is_connectedr   s-    
 DNN$.Rt~~7P7P7R3RSSr   rN   c                     t        t        j                  |      | _        |j	                  d      d u| _        | j                  j                         | _        t        j                         | _
        d| _        y )N
sslcontextF)r   r   	TransportrN   get_extra_inforJ   r   r3   rM   LockrO   rQ   )r   rN   s     r   connection_madezSMTPProtocol.connection_madey   sW    g//;"11,?tK $

 8 8 :$\\^r   r+   c                    t         |   |       | j                  sUt        d      }|r||_        | j
                  r5| j
                  j                         s| j
                  j                  |       d | _        d | _	        y r0   )
rI   r.   rQ   r
   	__cause__rM   r&   r-   rN   rO   )r   r+   smtp_excrR   s      r   r.   zSMTPProtocol.connection_lost   sj    $-.?@H%("$$T-B-B-G-G-I%%33H=!r   datac                    | j                   t        d|      | j                   j                         ry | j                  j	                  |       |j                  d      }|dk(  s||dz   |dz    dk(  ry 	 | j                         }|| j                   j                  |       y y # t        $ r%}| j                   j                  |       Y d }~y d }~ww xY w)Nz4data_received called without a response waiter set:    
         -)
rM   RuntimeErrorr&   rL   extendrfind_read_response_from_bufferr'   rD   r-   )r   rd   last_linebreakresponser+   s        r   data_receivedzSMTPProtocol.data_received   s      (FthO  ""'')D! E*b NQ&!);<D	;668H #%%00: $  	5!!//44	5s   7B& &	C/CCc                     t        d      }| j                  r5| j                  j                         s| j                  j                  |       y)NzUnexpected EOF receivedF)r
   rM   r&   r-   )r   r+   s     r   eof_receivedzSMTPProtocol.eof_received   s@    $%>?  )>)>)C)C)E!!//4 r   c                     | j                   rN| j                   j                         r4| j                   j                         s| j                   j                         S y)z
        Return any exception that has been set on the response waiter.

        Used to avoid 'Future exception was never retrieved' warnings
        N)rM   r&   	cancelled	exceptionr#   s    r   rU   z)SMTPProtocol._retrieve_response_exception   sI     !!%%**,))335((2244r   c                    d}t               }d}d}	 | j                  j                  d|      }|dk(  rnt        | j                  ||dz          }t	        |      t
        kD  rt        t        j                  d      	 t        |dd	       }|t	        |      z  }t	        |      r|j                  d       |j                  |dd j                  d             |d	d dk7  rd}n|r6t        |t        |      j!                  dd            }| j                  d|= |S y# t        $ r) t        t        j                  j                  d
|      dw xY w)z7Parse the actual response (if any) from the data bufferrg   r   FTrf   r   zResponse too longNrh   zMalformed SMTP response line: ri   s    	
rj   zutf-8surrogateescape)rK   rL   findbyteslenMAX_LINE_LENGTHr	   r   unrecognized_commandint
ValueErrorinvalid_responsevaluerl   stripr   decode)r   codemessageoffsetmessage_completeline_end_indexlinerp   s           r   rn   z'SMTPProtocol._read_response_from_buffer   sf   + !\\..uf=N#f~/ABCD4y?*+335H 48} c$iF7|u%NN48>>*56AayD #' 5 8 #eGn++G5FGH WfW%O+  +//554TH= s   <D 2Etimeoutc                   K   | j                   t        d      	 t        j                  | j                   |       d{   }	 | j                  	d| _         |S | j                  j                         | _         |S 7 ;# t        t        j                  f$ r}t        d      |d}~ww xY w# | j                  d| _         w | j                  j                         | _         w xY ww)a  
        Get a status response from the server.

        This method must be awaited once per command sent; if multiple commands
        are written to the transport without awaiting, response data will be lost.

        Returns an :class:`.response.SMTPResponse` namedtuple consisting of:
          - server response code (e.g. 250, or such, if all goes well)
          - server response string (multiline responses are converted to a
            single, multiline string).
        Nr1   z%Timed out waiting for server response)	rM   r
   r   wait_forTimeoutErrorr   rN   r   r3   )r   r   resultr+   s       r   read_responsezSMTPProtocol.read_response   s        (():;;		C"++D,A,A7KKF
 ~~%(,%  )-

(@(@(B% Lg223 	Y&'NOUXX	Y ~~%(,%(,

(@(@(B%sD   C!#A< A:A< 6C!:A< <B&B!!B&&B) )5CC!c                     | j                   | j                   j                         rt        d      t        | j                   d      st	        d| j                   d      | j                   j                  |       y )Nr1   writez
Transport z does not support writing.)rN   rY   r
   hasattrrk   r   )r   rd   s     r   r   zSMTPProtocol.write  sh    >>!T^^%>%>%@():;;t~~w/T^^..HI  	T"r   r   argsc                T  K   | j                   t        d      dj                  |      dz   }| j                   4 d{    | j                  |       |dk(  rd| _        | j                  |       d{   }ddd      d{    |S 7 M7 7 
# 1 d{  7  sw Y   S xY ww)zj
        Sends an SMTP command along with any args to the server, and returns
        a response.
        NServer not connected       
s   QUIT
Tr   )rO   r
   joinr   rQ   r   )r   r   r   commandrp   s        r   execute_commandzSMTPProtocol.execute_command  s      %()?@@))D/G+%%%JJw+%"&!///@@H &%  & A &%%% sW   <B(BB(3B5B6B:B(BB(BB(B%BB% B(r   c                   K   | j                   t        d      t        j                  d|      }t        j                  d|      }|j                  d      s|dz  }|dz  }| j                   4 d{    | j                  d       | j                  |       d{   }|j                  t        j                  k7  r t        |j                  |j                        | j                  |       | j                  |       d{   }|j                  t        j                  k7  r t        |j                  |j                        ddd      d{    |S 7 7 7 W7 # 1 d{  7  sw Y   S xY ww)z
        Sends an SMTP DATA command to the server, followed by encoded message content.

        Automatically quotes lines beginning with a period per RFC821.
        Lone \\r and \\n characters are converted to \\r\\n
        characters.
        Nr   r   s   ..s   .
s   DATA
r   )rO   r
   LINE_ENDINGS_REGEXsubPERIOD_REGEXendswithr   r   r   r   start_inputr   r   	completed)r   r   r   start_responserp   s        r   execute_data_commandz!SMTPProtocol.execute_data_command'  sB     %()?@@$((':""5'2(wG8%%%JJ{##'#5#5g#5#FFN""j&<&<<#N$7$79O9OPPJJw!///@@H}}
 4 44#HMM83C3CDD &%  &F
 A &%%% sn   A/E61E2E65'E EA'E EAE E6EE6E E E6 E3&E)'E3.E6tls_contextserver_hostnamec           	        K   | j                   rt        d      | j                  t        d      | j                  4 d{    | j	                  d       | j                  |       d{   }|j                  t        j                  k7  r t        |j                  |j                        | j                  | j                  j                         rt        d      	 | j                  j                  | j                  | |d||       d{   }|| _        ddd      d{    |S 7 7 7 !# t        t         j                  f$ r}t#        d	      |d}~wt$        $ r}t#        |j&                  d
         |d}~wt(        $ r/}|j&                  r|j&                  d
   }nd}t        |      |d}~ww xY w7 # 1 d{  7  sw Y   S xY ww)zG
        Puts the connection to the SMTP server into TLS mode.
        zAlready using TLS.Nr   s
   STARTTLS
r   r1   F)server_sider   ssl_handshake_timeoutz#Timed out while upgrading transportr   z.Connection was reset while upgrading transport)rJ   rk   rO   r
   r   r   r   r   readyr	   r   rN   rY   r   	start_tlsr   r   r   ConnectionAbortedErrorr   r2   )r   r   r   r   rp   tls_transportr+   r   s           r   r   zSMTPProtocol.start_tlsG  s     >>344%()?@@%%%JJ'!///@@H}}
 0 00+HMM8;K;KLL ~~%)B)B)D,->???&*jj&:&:NN %$3*1 '; ' !( +DN? &%B C &@! !'"6"67 W&'LMSVV) =&sxx{3<' ?88!hhqkGNG,W53>?1 &%%%B s   ?GD,G'F<,D.-A2F< .D2D0D2F<G%F:&G.F<0D22F7EF7#E<<F7*F22F77F<:G<GGG
Gr:   r>   )NN)"r?   r@   rA   r   r   rC   r   rE   r=   rV   propertyrX   rZ   BaseTransportr`   rD   r.   rz   rq   rs   BaseExceptionrU   r   rn   floatr   r   r   r   ssl
SSLContextstrr   __classcell__)rR   s   @r   r   r   [   s    59 w001  
 (<(< AW ,
 Td T T )>)>  4  "8I#6 "4 ";% ;D ;6d h}.E *H\,B *X8E? l 8#% #D # 8<%-e_	, :>'/	F *.#'	/^^/ "#/ %	/
 
/r   r   )rB   r   r   rer   typingr   r   r   errorsr   r   r	   r
   r   rp   r   r   __all__r|   compiler   r   Protocolr   BaseProtocolr   rF   r   r   <module>r      s      	 
 ( (  #   RZZ 89 rzz+&:"w'' :"z[#W%9%9 [r   