o
    	+il                     @  s>  d dl m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Zd dl	m
Z
mZmZmZmZmZmZ d dlmZ d dl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 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'm(Z(m)Z)m*Z*m+Z+ d dl,m-Z- ej.dkrd dlm/Z/ nd dl0m/Z/ zd dl1Z1W n e2y   e3dw eg eej4j5 f Z6ee)e+ge
d f Z7ee*ge7f Z8ee*e)e+ge
d f Z9ee:e:ee: B e;B f Z<d$ddZ=G dd dZ>G dd deZ?G dd de@ZAG dd de1jBe-ZCG dd dZDG d d! d!e1jEZFG d"d# d#e1jGZHdS )%    )annotationsN)	AwaitableCallable	GeneratorIterableMappingMutableMappingSequence)Future)AbstractContextManager)GeneratorType)AnyLiteral	TypedDict	TypeGuardcast)unquoteurljoin)StapledObjectStream)is_async_callable)ASGIAppMessageReceiveScopeSend)WebSocketDisconnect)      )SelfzThe starlette.testclient module requires the httpx package to be installed.
You can install this with:
    $ pip install httpx
appASGI2App | ASGI3AppreturnTypeGuard[ASGI3App]c                 C  s   t | r
t| dS t| S )N	__await__)inspectisclasshasattrr   r    r(   Q/var/www/html/psymed-ai/venv/lib/python3.10/site-packages/starlette/testclient.py	_is_asgi37   s   

r*   c                   @  s$   e Zd ZdZdddZdddZdS )
_WrapASGI2z7
    Provide an ASGI3 interface onto an ASGI2 app.
    r   ASGI2Appr!   Nonec                 C  
   || _ d S Nr'   )selfr   r(   r(   r)   __init__B      
z_WrapASGI2.__init__scoper   receiver   sendr   c                   s    |  |}|||I d H  d S r/   r'   )r0   r3   r4   r5   instancer(   r(   r)   __call__E   s   
z_WrapASGI2.__call__N)r   r,   r!   r-   )r3   r   r4   r   r5   r   r!   r-   )__name__
__module____qualname____doc__r1   r7   r(   r(   r(   r)   r+   =   s    
r+   c                   @  s   e Zd ZU ded< ded< dS )_AsyncBackendstrbackenddict[str, Any]backend_optionsN)r8   r9   r:   __annotations__r(   r(   r(   r)   r<   J   s   
 r<   c                   @  s   e Zd ZdddZdS )	_UpgradesessionWebSocketTestSessionr!   r-   c                 C  r.   r/   )rC   )r0   rC   r(   r(   r)   r1   P   r2   z_Upgrade.__init__N)rC   rD   r!   r-   )r8   r9   r:   r1   r(   r(   r(   r)   rB   O   s    rB   c                   @  s   e Zd ZdZdS )WebSocketDenialResponsez
    A special case of `WebSocketDisconnect`, raised in the `TestClient` if the
    `WebSocket` is closed before being accepted with a `send_denial_response()`.
    N)r8   r9   r:   r;   r(   r(   r(   r)   rE   T   s    rE   c                   @  s   e Zd Zd8d	d
Zd9ddZd:ddZd;ddZd<ddZd<ddZd=ddZ	d>d!d"Z
d?d@d&d'ZdAdBd.d/ZdCd0d1ZdDd2d3ZdEd4d5Zd?dFd6d7Zd)S )GrD   r   ASGI3Appr3   r   portal_factory_PortalFactoryTyper!   r-   c                 C  s"   || _ || _d | _|| _d | _d S r/   )r   r3   accepted_subprotocolrG   extra_headers)r0   r   r3   rG   r(   r(   r)   r1   _   s
   
zWebSocketTestSession.__init__c                 C  s   t  T}||   | _}|| j\}}||j ||j	|j
 | ddi |  }| | |dd | _|dd | _|| jd | | _| W  d    S 1 s[w   Y  d S )Ntypezwebsocket.connectsubprotocolheaders  )
contextlib	ExitStackenter_contextrG   portal
start_task_runcallbackresultcallcancelr5   r4   _raise_on_closegetrI   rJ   closepop_all
exit_stack)r0   stackrR   futcsmessager(   r(   r)   	__enter__k   s   


$zWebSocketTestSession.__enter__argsr   bool | Nonec                 G  s   | j j| S r/   )r]   __exit__r0   rc   r(   r(   r)   re   z   s   zWebSocketTestSession.__exit__task_status'anyio.abc.TaskStatus[anyio.CancelScope]c          	        s6  t tj}|\}}t tj}|\}}|z |_ |M |; t  '}|| _|| _|| | | j	|j
|jI dH  t  I dH  W d   n1 sOw   Y  W d   n1 s^w   Y  W d   n1 smw   Y  W d   n1 s|w   Y  W d   dS W d   dS 1 sw   Y  dS )zE
        The sub-thread in which the websocket session runs.
        N)anyiocreate_memory_object_streammathinfCancelScope_receive_tx_send_rxstartedr   r3   r4   r5   sleep_forever)	r0   rg   r5   send_txsend_rxr4   
receive_tx
receive_rxr`   r(   r(   r)   rT   }   s$   "
  P zWebSocketTestSession._runra   r   c                 C  s   |d dkrt |dd|ddd|d dkrJ|d	 }|d
 }g }	 |  }|d dks1J ||d  |dds?nq%t||d|dd S )NrK   zwebsocket.closecoderN   reason )rv   rw   zwebsocket.http.response.startstatusrM   Tzwebsocket.http.response.bodybody	more_bodyF    )status_coderM   content)r   rZ   r4   appendrE   join)r0   ra   r}   rM   rz   r(   r(   r)   rY      s   z$WebSocketTestSession._raise_on_closec                 C  s   | j | jj| d S r/   )rR   rW   rn   r5   r0   ra   r(   r(   r)   r5         zWebSocketTestSession.senddatar=   c                 C     |  d|d d S )Nwebsocket.receiverK   textr5   r0   r   r(   r(   r)   	send_text      zWebSocketTestSession.send_textbytesc                 C  r   )Nr   rK   r   r   r   r(   r(   r)   
send_bytes   r   zWebSocketTestSession.send_bytesr   modeLiteral['text', 'binary']c                 C  sF   t j|ddd}|dkr| d|d d S | d|dd d S )	N),:F)
separatorsensure_asciir   r   r   utf-8r   )jsondumpsr5   encode)r0   r   r   r   r(   r(   r)   	send_json   s   zWebSocketTestSession.send_jsonrN   Nrv   intrw   
str | Nonec                 C  s   |  d||d d S )Nzwebsocket.disconnect)rK   rv   rw   r   )r0   rv   rw   r(   r(   r)   r[      r   zWebSocketTestSession.closec                 C  s   | j | jjS r/   )rR   rW   ro   r4   r0   r(   r(   r)   r4      s   zWebSocketTestSession.receivec                 C      |   }| | tt|d S )Nr   )r4   rY   r   r=   r   r(   r(   r)   receive_text      
z!WebSocketTestSession.receive_textc                 C  r   )Nr   )r4   rY   r   r   r   r(   r(   r)   receive_bytes   r   z"WebSocketTestSession.receive_bytesc                 C  s<   |   }| | |dkr|d }n|d d}t|S )Nr   r   r   )r4   rY   decoder   loads)r0   r   ra   r   r(   r(   r)   receive_json   s   


z!WebSocketTestSession.receive_json)r   rF   r3   r   rG   rH   r!   r-   )r!   rD   )rc   r   r!   rd   )rg   rh   r!   r-   ra   r   r!   r-   )r   r=   r!   r-   )r   r   r!   r-   )r   )r   r   r   r   r!   r-   )rN   N)rv   r   rw   r   r!   r-   r!   r   )r!   r=   )r!   r   )r   r   r!   r   )r8   r9   r:   r1   rb   re   rT   rY   r5   r   r   r   r[   r4   r   r   r   r(   r(   r(   r)   rD   ^   s    










rD   c                   @  s&   e Zd Z		ddddZdddZdS )_TestClientTransportTrx   r   rF   rG   rH   raise_server_exceptionsbool	root_pathr=   clienttuple[str, int]	app_stater?   r!   r-   c                C  s(   || _ || _|| _|| _|| _|| _d S r/   )r   r   r   rG   r   r   )r0   r   rG   r   r   r   r   r(   r(   r)   r1      s   

z_TestClientTransport.__init__requesthttpx.Requesthttpx.Responsec                   s  j j}j jjdd}j j}j j}j jjdd}ddddd| }d|v r6|dd\}}	t|	}
n|}|}
dj	v rBg }n|
|krNd	|
 fg}nd	| d|
 
 fg}|d
d j	 D 7 }|dv rj	dd }|d u rxg }n
dd |dD }dt||ddd | j||
 || j||
g|| j di id}t| j|| j}t|ddjt||ddd | j||
 || j||
gdi i| j d}dddt id d  d'fdd}d( fd!d"}z&|  }|tj|| j||| W d    n	1 sw   Y  W n ty6 } z| jr,|W Y d }~nd }~ww | jrCsBJ d#nsNd$g t d%td   d< tj!d)i d&i}d urp|_" |_#|S )*Nascii)encodingP   i  )httpwshttpswssr      hosts   hostc                 S  s$   g | ]\}}|   | fqS r(   )lowerr   .0keyvaluer(   r(   r)   
<listcomp>   s   $ z7_TestClientTransport.handle_request.<locals>.<listcomp>>   r   r   sec-websocket-protocolc                 S  s   g | ]}|  qS r(   )strip)r   r   r(   r(   r)   r      s    r   	websocket   ?r   zwebsocket.http.response)rK   pathraw_pathr   schemequery_stringrM   r   serversubprotocolsstate
extensionsr   z1.1http.response.debug)rK   http_versionmethodr   r   r   r   r   rM   r   r   r   r   Fstreamr!   r   c                    s   r  s I d H  ddiS   } t| tr!| d}n5| d u r(d}n.t| trTz| d }t|tr=|d}d|ddW S  tyS   dddd Y S w | }dd|dS )	NrK   zhttp.disconnectr   r|   zhttp.requestT)rK   rz   r{   )rK   rz   )	is_setwaitread
isinstancer=   r   r   r5   StopIteration)rz   
body_byteschunk)r   request_completeresponse_completer(   r)   r4   $  s.   





z4_TestClientTransport.handle_request.<locals>.receivera   r-   c                   s   | d dkr$rJ d| d d< dd |  dg D d< d	d S | d d
kras0J d r8J d|  dd}|  dd}jdkrPd | |s_d d   d S d S | d dkru| d d | d d  d S d S )NrK   zhttp.response.startz1Received multiple "http.response.start" messages.ry   r}   c                 S  s    g | ]\}}|  |  fqS r(   )r   r   r(   r(   r)   r   F  s     zE_TestClientTransport.handle_request.<locals>.send.<locals>.<listcomp>rM   Tzhttp.response.bodyz<Received "http.response.body" without "http.response.start".z7Received "http.response.body" after response completed.rz   r|   r{   FHEADr   r   r   infotemplatecontext)rZ   r   r   writeseekset)ra   rz   r{   )r   
raw_kwargsr   r   response_startedr   r(   r)   r5   @  s*   
z1_TestClientTransport.handle_request.<locals>.sendz(TestClient did not receive any response.i  )r}   rM   r   r   r   r   r(   )$urlr   netlocr   r   r   querysplitr   rM   r   multi_itemsrZ   r   r   r   r   copyrD   r   rG   rB   r   ioBytesIOrW   ri   EventBaseExceptionr   httpx
ByteStreamr   Responser   r   )r0   r   r   r   r   r   r   default_portr   port_stringportrM   rL   r   r3   rC   r4   r5   rR   excresponser(   )r   r   r   r   r   r   r   r)   handle_request   s   



z#_TestClientTransport.handle_requestN)Trx   )r   rF   rG   rH   r   r   r   r=   r   r   r   r?   r!   r-   )r   r   r!   r   )r8   r9   r:   r1   r   r(   r(   r(   r)   r      s
    r   c                      s   e Zd ZU dZded< dZded< 					
					d^d_ fd d!Zejd`d#d$Z	ddddddde
jje
jje
jjdd%da fd;d<Zddde
jje
jje
jjdd=db fd>d?Zddde
jje
jje
jjdd=db fd@dAZddde
jje
jje
jjdd=db fdBdCZddddddde
jje
jje
jjdd%dc fdDdEZddddddde
jje
jje
jjdd%dc fdFdGZddddddde
jje
jje
jjdd%dc fdHdIZddde
jje
jje
jjdd=db fdJdKZ	ddde fdPdQZdfdSdTZdgdVdWZdhdXdYZdhdZd[Zdhd\d]Z  ZS )i
TestClientFzFuture[None]taskNzanyio.abc.BlockingPortal | NonerR   http://testserverTrx   asyncio
testclientiP  r   r   base_urlr=   r   r   r   r>   Literal['asyncio', 'trio']r@   dict[str, Any] | Nonecookieshttpx._types.CookieTypes | NonerM   dict[str, str] | Nonefollow_redirectsr   r   r!   r-   c                   s   t ||pi d| _t|r|}n	tt|}t|}|| _i | _t| j| j	||| j|
d}|d u r2i }|
dd t j||||	|d d S )N)r>   r@   )rG   r   r   r   r   z
user-agentr   )r   rM   	transportr   r   )r<   async_backendr*   r   r,   r+   r   r   r   _portal_factory
setdefaultsuperr1   )r0   r   r   r   r   r>   r@   r   rM   r   r   asgi_appr  	__class__r(   r)   r1   u  s2   

zTestClient.__init__/Generator[anyio.abc.BlockingPortal, None, None]c                 c  sX    | j d ur| j V  d S tjjdi | j}|V  W d    d S 1 s%w   Y  d S )Nr(   )rR   ri   from_threadstart_blocking_portalr  )r0   rR   r(   r(   r)   r    s   
"zTestClient._portal_factoryr~   r   filesr   paramsrM   r   authr   timeoutr   r   r   httpx._types.URLTypesr~   "httpx._types.RequestContent | Noner   _RequestData | Noner   httpx._types.RequestFiles | Noner   r   r  #httpx._types.QueryParamTypes | Nonehttpx._types.HeaderTypes | Noner  7httpx._types.AuthTypes | httpx._client.UseClientDefault%bool | httpx._client.UseClientDefaultr  :httpx._types.TimeoutTypes | httpx._client.UseClientDefaultr   r   c                  sF   |t jurtdt | |}t j|||||||||	|
|||dS )NzYou should not use the 'timeout' argument with the TestClient. See https://github.com/Kludex/starlette/issues/1108 for more information.r  )r   USE_CLIENT_DEFAULTwarningswarnDeprecationWarning
_merge_urlr  r   )r0   r   r   r~   r   r  r   r  rM   r   r  r   r  r   r  r(   r)   r     s*   

zTestClient.requestr  rM   r   r  r   r  r   c          	   
        t  j||||||||dS Nr  )r  rZ   	r0   r   r  rM   r   r  r   r  r   r  r(   r)   rZ        zTestClient.getc          	   
     r   r!  )r  optionsr"  r  r(   r)   r$    r#  zTestClient.optionsc          	   
     r   r!  )r  headr"  r  r(   r)   r%    r#  zTestClient.headc                  $   t  j|||||||||	|
||dS Nr  )r  postr0   r   r~   r   r  r   r  rM   r   r  r   r  r   r  r(   r)   r(       zTestClient.postc                  r&  r'  )r  putr)  r  r(   r)   r+  1  r*  zTestClient.putc                  r&  r'  )r  patchr)  r  r(   r)   r,  P  r*  zTestClient.patchc          	   
     r   r!  )r  deleter"  r  r(   r)   r-  o  r#  zTestClient.deleter   Sequence[str] | NonekwargsrD   c              
     s   t d|}|di }|dd |dd |dd |d ur*|d	d
| ||d< zt jd|fi | W td tyT } z
|j}W Y d }~|S d }~ww )Nzws://testserverrM   
connectionupgradezsec-websocket-keyztestserver==zsec-websocket-version13r   z, GETzExpected WebSocket upgrade)	r   rZ   r  r   r  r   rB   rC   RuntimeError)r0   r   r   r/  rM   r   rC   r  r(   r)   websocket_connect  s    
zTestClient.websocket_connectr   c                   s   t  f}|tjjdi j _ |jdfdd}t	t
j}t	t
j}g ||R D ]}||j q2t| _t| _ j_ j |jd fdd}| _W d    S 1 smw   Y  S )	Nr!   r-   c                     s
   d  _ d S r/   )rR   r(   r   r(   r)   reset_portal  s   
z*TestClient.__enter__.<locals>.reset_portalc                     s     j d S r/   )rW   wait_shutdownr(   rR   r0   r(   r)   r7    s   z+TestClient.__enter__.<locals>.wait_shutdownr(   r!   r-   )rO   rP   rQ   ri   r
  r  r  rR   rU   rj   rk   rl   r[   r   stream_sendstream_receivestart_task_soonlifespanr   rW   wait_startupr\   r]   )r0   r^   r6  r5   r4   channelr7  r(   r8  r)   rb     s,   
 



zTestClient.__enter__rc   c                 G  s   | j   d S r/   )r]   r[   rf   r(   r(   r)   re     s   zTestClient.__exit__c              	     sX   d| j d}z| || jj| jjI d H  W | jd I d H  d S | jd I d H  w )Nr=  )rK   r   )r   r   r;  r4   r:  r5   )r0   r3   r(   r(   r)   r=    s
   *zTestClient.lifespanc                   sb    j ddiI d H  d	 fdd}| I d H }|d dv s!J |d dkr/| I d H  d S d S )
NrK   zlifespan.startupr!   r   c                    (    j  I d H } | d u r j  | S r/   r:  r4   r   rV   ra   r   r(   r)   r4     
   
z(TestClient.wait_startup.<locals>.receive)zlifespan.startup.completelifespan.startup.failedrD  r!   r   r;  r5   r0   r4   ra   r(   r   r)   r>    s   zTestClient.wait_startupc                   sb   d	 fdd} j ddiI d H  | I d H }|d dv s!J |d dkr/| I d H  d S d S )
Nr!   r   c                    r@  r/   rA  rB  r   r(   r)   r4     rC  z)TestClient.wait_shutdown.<locals>.receiverK   zlifespan.shutdown)zlifespan.shutdown.completelifespan.shutdown.failedrH  rE  rF  rG  r(   r   r)   r7    s   zTestClient.wait_shutdown)	r   Trx   r   NNNTr   )r   r   r   r=   r   r   r   r=   r>   r   r@   r   r   r   rM   r   r   r   r   r   r!   r-   )r!   r	  )r   r=   r   r  r~   r  r   r  r  r  r   r   r  r  rM   r  r   r   r  r  r   r  r  r  r   r   r!   r   )r   r  r  r  rM   r  r   r   r  r  r   r  r  r  r   r   r!   r   )r   r  r~   r  r   r  r  r  r   r   r  r  rM   r  r   r   r  r  r   r  r  r  r   r   r!   r   r/   )r   r=   r   r.  r/  r   r!   rD   )r!   r   )rc   r   r!   r-   r9  )r8   r9   r:   __test__rA   rR   r1   rO   contextmanagerr  r   _clientr  r   rZ   r$  r%  r(  r+  r,  r-  r5  rb   re   r=  r>  r7  __classcell__r(   r(   r  r)   r   p  s   
 (,###



r   )r   r    r!   r"   )I
__future__r   rO   r$   r   r   rk   sysr  collections.abcr   r   r   r   r   r   r	   concurrent.futuresr
   r   typesr   typingr   r   r   r   r   urllib.parser   r   ri   	anyio.abcanyio.from_threadanyio.streams.stapledr   starlette._utilsr   starlette.typesr   r   r   r   r   starlette.websocketsr   version_infor   typing_extensionsr   ModuleNotFoundErrorr4  abcBlockingPortalrH   ASGIInstancer,   rF   r=   r   _RequestDatar*   r+   r<   	ExceptionrB   r   rE   rD   BaseTransportr   Clientr   r(   r(   r(   r)   <module>   s`    $



i *