a
    xdT`                     @   s  d Z ddlZddlZ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 ddl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mZmZmZmZ ddlZejrdd
lmZmZ e dZ!G dd deZ"G dd deZ#e$dkre%e" e  dS )z5Non-blocking HTTP client implementation using pycurl.    N)BytesIO)httputil)ioloop)utf8
native_str)HTTPRequestHTTPResponse	HTTPErrorAsyncHTTPClientmain)app_log)DictAnyCallableUnionOptional)DequeTupleztornado.curl_httpclientc                       s^  e Zd Zd.eeeeef  dd fddZdd fddZ	e
eegdf dd	d
dZeeeeddddZeddddZeeddddZddddZddddZddddZddddZd/ejee ee ddddZedd d!d"Zejdd#d$Zeje
eejdd%d&d'Zejeegdf edd(d)d*Zeedd+d,d-Z   Z!S )0CurlAsyncHTTPClient
   N)max_clientsdefaultsreturnc                    s   t  j|d t  _ jtj j  jtj j	  fddt
|D  _ jd d   _t  _i  _d  _t jd _ j  t } j|  j| d S )N)r   c                    s   g | ]}   qS  )_curl_create).0iselfr   O/var/www/html/Ranjet/env/lib/python3.9/site-packages/tornado/curl_httpclient.py
<listcomp>9       z2CurlAsyncHTTPClient.initialize.<locals>.<listcomp>  )super
initializepycurlZ	CurlMulti_multisetoptZM_TIMERFUNCTION_set_timeoutZM_SOCKETFUNCTION_handle_socketrange_curls
_free_listcollectionsdeque	_requests_fds_timeoutr   ZPeriodicCallback_handle_force_timeout_force_timeout_callbackstartCurl
add_handleremove_handle)r   r   r   Zdummy_curl_handle	__class__r   r   r$   1   s"    

zCurlAsyncHTTPClient.initialize)r   c                    sZ   | j   | jd ur"| j| j | jD ]}|  q(| j  t   d | _ d | _d S N)	r3   stopr1   io_loopremove_timeoutr+   closer&   r#   r   curlr8   r   r   r>   S   s    





zCurlAsyncHTTPClient.close)requestcallbackr   c                 C   s.   | j ||| j f |   | d d S Nr   )r/   appendr<   time_process_queuer(   )r   rA   rB   r   r   r   
fetch_implb   s    zCurlAsyncHTTPClient.fetch_impl)eventfdmultidatar   c              	   C   s   t jtjjt jtjjt jtjjt j	tjjtjjB i}|t j
kr^|| jv r| j| | j|= n:|| }|| jv r|| j| | j|| j| || j|< dS )z_Called by libcurl when it wants to change the file descriptors
        it cares about.
        N)r%   Z	POLL_NONEr   IOLoopNONEZPOLL_INREADZPOLL_OUTWRITEZ
POLL_INOUTZPOLL_REMOVEr0   r<   Zremove_handleradd_handler_handle_events)r   rH   rI   rJ   rK   Z	event_mapZioloop_eventr   r   r   r)   i   s    





	
z"CurlAsyncHTTPClient._handle_socket)msecsr   c                 C   s<   | j dur| j| j  | j| j |d  | j| _ dS )z(Called by libcurl to schedule a timeout.Ng     @@)r1   r<   r=   Zadd_timeoutrE   _handle_timeout)r   rR   r   r   r   r(      s
    
z CurlAsyncHTTPClient._set_timeout)rI   eventsr   c              
   C   s   d}|t jj@ r|tjO }|t jj@ r0|tjO }z| j||\}}W n0 tj	yv } z|j
d }W Y d}~n
d}~0 0 |tjkr0qq0|   dS )zXCalled by IOLoop when there is activity on one of our
        file descriptors.
        r   N)r   rL   rN   r%   Z
CSELECT_INrO   ZCSELECT_OUTr&   socket_actionerrorargsE_CALL_MULTI_PERFORM_finish_pending_requests)r   rI   rT   actionretnum_handleser   r   r   rQ      s    

 
z"CurlAsyncHTTPClient._handle_eventsc              
   C   s   d| _ z| jtjd\}}W n0 tjyN } z|jd }W Y d}~n
d}~0 0 |tjkrq^q|   | j	 }|dkr| 
| dS )z7Called by IOLoop when the requested timeout has passed.Nr   )r1   r&   rU   r%   ZSOCKET_TIMEOUTrV   rW   rX   rY   timeoutr(   )r   r[   r\   r]   Znew_timeoutr   r   r   rS      s     

z#CurlAsyncHTTPClient._handle_timeoutc              
   C   s^   z| j  \}}W n0 tjyB } z|jd }W Y d}~n
d}~0 0 |tjkr qRq |   dS )zpCalled by IOLoop periodically to ask libcurl to process any
        events it may have forgotten about.
        r   N)r&   Z
socket_allr%   rV   rW   rX   rY   )r   r[   r\   r]   r   r   r   r2      s     
z)CurlAsyncHTTPClient._handle_force_timeoutc                 C   sZ   | j  \}}}|D ]}| | q|D ]\}}}| ||| q(|dkr qNq |   dS )zbProcess any requests that were completed by the last
        call to multi.socket_action.
        r   N)r&   Z	info_read_finishrF   )r   Znum_qZok_listZerr_listr@   Zerrnumerrmsgr   r   r   rY      s    z,CurlAsyncHTTPClient._finish_pending_requestsc              
   C   s   d}| j r| jr|d7 }| j  }| j \}}}t t |||t | j	  d|_
z | |||j
d |j
d  W nB ty } z*| j | |t|d|d W Y d }~qd }~0 0 | j| q|s qq d S )Nr      )headersbufferrA   rB   queue_start_timecurl_start_timecurl_start_ioloop_timerc   rb   W  )rA   coderV   )r,   r/   poppopleftr   HTTPHeadersr   rE   r<   currentinfo_curl_setup_request	ExceptionrD   r   r&   r6   )r   startedr@   rA   rB   rd   r]   r   r   r   rF      s4    
		(z"CurlAsyncHTTPClient._process_queue)r@   
curl_errorcurl_messager   c           
      C   sb  |j }d |_ | j| | j| |d }|rj|d us<J t||}|d usRJ |j}d }|  d }n&d }|t	j
}|t	j}|d t|d |d  |t	j|t	j|t	j|t	j|t	j|t	j|t	jd}	zN|d t|d ||d ||||d d	d | j |d  |d
 |	d
 W n" ty\   | |d  Y n0 d S )Nrc   r   rf   rd   )queueZ
namelookupconnectZ
appconnectZpretransferZstarttransfertotalredirectrB   rA   rb   zX-Http-Reasonre   )
rA   rh   rb   rc   effective_urlrV   reasonZrequest_time
start_time	time_info)rm   r&   r7   r,   rD   	CurlErrorrh   r>   getinfor%   Z	HTTP_CODEZEFFECTIVE_URLseekdictZNAMELOOKUP_TIMEZCONNECT_TIMEZAPPCONNECT_TIMEZPRETRANSFER_TIMEZSTARTTRANSFER_TIMEZ
TOTAL_TIMEZREDIRECT_TIMEr   getr<   rE   ro   handle_callback_exception)
r   r@   rq   rr   rm   rc   rV   rh   rw   rz   r   r   r   r_     sX    









zCurlAsyncHTTPClient._finish)rB   r   c                 C   s   t jd|dd d S )NzException in callback %rT)exc_info)r   rV   )r   rB   r   r   r   r   7  s    z-CurlAsyncHTTPClient.handle_callback_exceptionc                 C   sl   t  }ttjr2|t jd |t j| j	 t
t drh|t jt jt jB  |t jt jt jB  |S )Nra   	PROTOCOLS)r%   r5   curl_logisEnabledForloggingDEBUGr'   VERBOSEZDEBUGFUNCTION_curl_debughasattrr   Z
PROTO_HTTPZPROTO_HTTPSZREDIR_PROTOCOLSr?   r   r   r   r   :  s    z CurlAsyncHTTPClient._curl_create)r@   rA   rc   rb   r   c                    s    tjtj djvr(djd< djvr<djd<   tjdd j D    tjt	
j|j jrtttf tdfdd}n|j}  tj|   tjj   tjj jd usJ   tjtd	j  jd usJ   tjtd	j  jr<  tjtj n  tjd
 jrb  tjj j rz  tj!d n  tj!d  j"rFj#rF  tj$j"   tj%j# j&rj'd usJ t()j&j'}  tj*| j+d u sj+dkr  tj,tj- n,j+dkr6  tj,tj. nt/dj+ n@z 0tj$ W n" t1yx     tj$d Y n0  0tj* j2r  tj3d   tj4d n  tj3d   tj4d j5d ur  tj6j5 n j7du r  tj8tj9 n  tj8tj: tj;tj<tj=tj>d}t?g d}|@ D ]}	  |	d q>jA|v r~ 0tjB   |jA d n4jCsjA|v r  tjBjA ntDdjA jAdv }
jEd u}jCs|
r|r|r|
st/d|
rdndjAf |
s|rjAdkr"t/dtFtGjEp0dtd d fdd}  tjHjI   tjJ| jAdkr  tjKtLjEpd n(  tj=d   tjMtLjEpd jNd urbjOd usJ jPd u sjPdkr   tjQtj- n,jPdkr  tjQtj. nt/d jP t()jNjO}  tjR| tSTd!jAjjN n 0tjR tSTd"jAj jUd ur  tjVjU jWd ur  tjXjW jYd urt/d#tZ[ dkr  tj\d j]d ur]  d S )$NZExpect ZPragmac                 S   s0   g | ](\}}d t |dt |df qS )s   %s: %sASCIIz	ISO8859-1)r   encode)r   kvr   r   r   r    `  s   z;CurlAsyncHTTPClient._curl_setup_request.<locals>.<listcomp>)br   c                    s&    j d usJ j j |  t| S r:   )streaming_callbackr<   add_callbacklen)r   )rA   r   r   r   write_functiono  s    z?CurlAsyncHTTPClient._curl_setup_request.<locals>.write_functionr"   z Mozilla/5.0 (compatible; pycurl)zgzip,deflatebasicdigestzUnsupported proxy_auth_mode %sra      r   F)GETPOSTPUTHEAD)DELETEOPTIONSPATCHTzunknown method )r   r   r   zLBody must %sbe None for method %s (unless allow_nonstandard_methods is true)znot r   z!Body must be None for GET request)cmdr   c                    s   |  j krd d S rC   )ZIOCMD_RESTARTREADr}   )r   )r@   request_bufferr   r   ioctl  s    
z6CurlAsyncHTTPClient._curl_setup_request.<locals>.ioctlr   zUnsupported auth_mode %sz%s %s (username: %r)%s %sz,ssl_options not supported in curl_httpclient)^r'   r%   URLr   urlrb   Z
HTTPHEADERget_allZHEADERFUNCTION	functoolspartial_curl_header_callbackheader_callbackr   r   bytes	bytearrayintwriteZWRITEFUNCTIONZFOLLOWLOCATIONZfollow_redirectsZ	MAXREDIRSmax_redirectsconnect_timeoutZCONNECTTIMEOUT_MSrequest_timeoutZ
TIMEOUT_MS
user_agentZ	USERAGENTZnetwork_interfaceZ	INTERFACEZdecompress_responseENCODINGZ
proxy_hostZ
proxy_portZPROXYZ	PROXYPORTZproxy_usernameZproxy_passwordr   Zencode_username_passwordZPROXYUSERPWDZproxy_auth_modeZ	PROXYAUTHZHTTPAUTH_BASICZHTTPAUTH_DIGEST
ValueErrorZunsetopt	TypeErrorZvalidate_certZSSL_VERIFYPEERZSSL_VERIFYHOSTca_certsZCAINFOZ
allow_ipv6Z	IPRESOLVEZIPRESOLVE_V4ZIPRESOLVE_WHATEVERZHTTPGETr   ZUPLOADZNOBODYsetvaluesmethodZCUSTOMREQUESTZallow_nonstandard_methodsKeyErrorbodyr   r   ZREADFUNCTIONreadZIOCTLFUNCTIONZPOSTFIELDSIZEr   Z
INFILESIZEZauth_usernameZauth_passwordZ	auth_modeZHTTPAUTHZUSERPWDr   debugclient_certZSSLCERTZ
client_keyZSSLKEYZssl_options	threadingactive_countZNOSIGNALZprepare_curl_callback)r   r@   rA   rc   rb   r   credentialsZcurl_optionsZcustom_methodsoZbody_expectedZbody_presentr   Zuserpwdr   )r@   rA   r   r   r   rn   F  s
   




	
 


	z'CurlAsyncHTTPClient._curl_setup_request)rb   r   header_line_bytesr   c                 C   s   t |d}|d ur$| j|| | }|drr|  zt|\}}}d| }W n tj	yp   Y d S 0 |szd S |
| d S )Nlatin1zHTTP/zX-Http-Reason: %s)r   decoder<   r   rstrip
startswithclearr   Zparse_response_start_lineZHTTPInputError
parse_line)r   rb   r   r   Zheader_line__rx   r   r   r   r     s    
z)CurlAsyncHTTPClient._curl_header_callback)
debug_type	debug_msgr   c                 C   sv   d}|dkr&t |}td|  nL|dv rXt |}| D ]}td|| | q>n|dkrrtd|| | d S )N)I<>r   r   r   z%s)ra   r   r      z%s %r)r   r   r   strip
splitlines)r   r   r   Zdebug_typesliner   r   r   r   3  s    zCurlAsyncHTTPClient._curl_debug)r   N)NN)"__name__
__module____qualname__r   r   r   strr   r$   r>   r   r   r   rG   r   r)   r(   rQ   rS   r2   rY   rF   r%   r5   r_   r   r   r   r   rk   rn   r   r   __classcell__r   r   r8   r   r   0   sN    ",  6 Yr   c                   @   s   e Zd ZeeddddZdS )r{   N)errnomessager   c                 C   s   t | d| || _d S )Nrg   )r	   __init__r   )r   r   r   r   r   r   r   A  s    zCurlError.__init__)r   r   r   r   r   r   r   r   r   r   r{   @  s   r{   __main__)&__doc__r-   r   r   r%   r   rE   ior   Ztornador   r   Ztornado.escaper   r   Ztornado.httpclientr   r   r	   r
   r   Ztornado.logr   typingr   r   r   r   r   TYPE_CHECKINGr   r   	getLoggerr   r   r{   r   	configurer   r   r   r   <module>   s4   
    

