a
    zex                     @   s  d dl mZ d dlmZ d dlmZ d dl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 d d	lmZ d d
lmZ d dlmZmZ d dlmZ d dlmZ d dlmZmZmZ d dlm Z  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 G dd deZ(G dd deZ)dd Z*dd Z+e*dfddZ,dd Z-G dd  d eZ.G d!d" d"eZ/G d#d$ d$eZ0G d%d& d&eZ1G d'd( d(e1Z2G d)d* d*eZ3e4d+kre 5  dS ),    )mock)support)socket_helper)NoLogRequestHandler)TestCase)setup_testing_defaults)Headers)BaseHandlerBaseCGIHandlerSimpleHandler)util)	validator)
WSGIServerWSGIRequestHandler)make_server)HTTPConnection)StringIOBytesIOBufferedReader)
BaseServer)python_implementationNc                   @   s    e Zd ZdZdd Zdd ZdS )
MockServerzNon-socket HTTP serverc                 C   s   t | || |   d S N)r   __init__server_bind)selfserver_addressZRequestHandlerClass r   '/usr/lib/python3.9/test/test_wsgiref.pyr      s    zMockServer.__init__c                 C   s"   | j \}}|| _|| _|   d S r   )r   Zserver_nameZserver_portsetup_environ)r   hostportr   r   r   r   !   s    
zMockServer.server_bindN)__name__
__module____qualname____doc__r   r   r   r   r   r   r      s   r   c                   @   s    e Zd ZdZdd Zdd ZdS )MockHandlerzNon-socket HTTP handlerc                 C   s   | j | _| j\| _| _d S r   )request
connectionZrfileZwfiler   r   r   r   setup*   s    zMockHandler.setupc                 C   s   d S r   r   r)   r   r   r   finish.   s    zMockHandler.finishN)r"   r#   r$   r%   r*   r+   r   r   r   r   r&   (   s   r&   c                 C   s   |dddg dgS )N200 OKContent-Typez
text/plainDatezMon, 05 Jun 2006 18:49:54 GMT   Hello, world!r   environZstart_responser   r   r   	hello_app2   s
    r4   c                 C   s2   |dddg d | d | d | d gdgS )	Nr,   r-   r/   ;ZHTTP_X_TEST_HEADERQUERY_STRING	PATH_INFO
iso-8859-1)joinencoder2   r   r   r   
header_app:   s    r;   s   GET / HTTP/1.0

c                 C   sh   t dd| tt}tt|}t }tj}t  }t_z|||fd W |t_n|t_0 |	 |	 fS )N P   )	127.0.0.1i"  )
r   r   r&   r   r   sysstderrr   Zfinish_requestgetvalue)appdataserverinpoutZolderrerrr   r   r   	run_amockE   s    rH   c                 C   s   |  }d}|D ]}|| |ks"t |d7 }qz||  W n tyJ   Y n0 t d|zttf W n tyt   Y n\0 |  }t||urt |D ]}t||kst qzt| W n ty   Y n0 t d|dS )a  Utility to compare a generic 2.1/2.2+ iterator with an iterable

    If running under Python 2.2+, this tests the iterator using iter()/next(),
    as well as __getitem__.  'make_it' must be a function returning a fresh
    iterator to be tested (since this may test the iterator twice).r      zToo many items from __getitem__zToo many items from .__next__()N)AssertionError
IndexErroriterStopIteration	NameErrornext)make_itmatchitnitemr   r   r   compare_generic_iterS   s.    

rU   c                   @   sf   e Zd ZdddZdd Zdd Zdd	 Zd
d Zdd Zdd Z	dd Z
dd Zdd Zdd ZdS )IntegrationTestsTc                 C   sF   t  d tj d  }| |d| d |r0dp2d d d d S )	N/r   z(HTTP/1.0 200 OK
Server: WSGIServer/0.2 zA
Content-Type: text/plain
Date: Mon, 05 Jun 2006 18:49:54 GMT
zContent-Length: 13
r<   z
Hello, world!r8   )r   r?   versionsplitassertEqualr:   )r   rF   
has_lengthpyverr   r   r   check_helloz   s     
zIntegrationTests.check_helloc                 C   s   t  \}}| | d S r   )rH   r]   r   rF   rG   r   r   r   test_plain_hello   s    
z!IntegrationTests.test_plain_helloc                 C   s*   d}t t|\}}| | d d d S )Nsm   GET /p%61th/?query=test HTTP/1.0
X-Test-Header: Python test 
X-Test-Header: Python test 2
Content-Length: 0

s+   Python test,Python test 2;query=test;/path/)rH   r;   rZ   
splitlines)r   r'   rF   rG   r   r   r   test_environ   s    
zIntegrationTests.test_environc                 C   s2   t ddd  d d\}}| | d d d S )Ns   GET    xi  s    HTTP/1.0

rC   r   s!   HTTP/1.0 414 Request-URI Too Long)rH   rZ   ra   r^   r   r   r   test_request_length   s    z$IntegrationTests.test_request_lengthc                 C   s"   t tt\}}| j|dd d S )NF)r[   )rH   r   r4   r]   r^   r   r   r   test_validated_hello   s    z%IntegrationTests.test_validated_helloc                 C   s@   dd }t t|\}}| |d | | d d d S )Nc                 S   s   |dd dgS )Nr,   r-   zHello, world!r   r2   r   r   r   bad_app   s    
z>IntegrationTests.test_simple_validation_error.<locals>.bad_app;   A server error occurred.  Please contact the administrator.z^AssertionError: Headers (('Content-Type', 'text/plain')) must be of type list: <class 'tuple'>rH   r   
assertTrueendswithrZ   ra   r   rg   rF   rG   r   r   r   test_simple_validation_error   s    
z-IntegrationTests.test_simple_validation_errorc              	   C   s   dd }g d}|D ]h\}}| j |dD t||\}}| |d | | d | W d    q1 sr0    Y  qd S )Nc                    s    fdd}|S )Nc                    s   | dg dgS )Nr.   ztext/plain; charset=utf-8r1   r   r2   statusr   r   rg      s    zWIntegrationTests.test_status_validation_errors.<locals>.create_bad_app.<locals>.bad_appr   )rq   rg   r   rp   r   create_bad_app   s    zFIntegrationTests.test_status_validation_errors.<locals>.create_bad_app))Z200z4AssertionError: Status must be at least 4 characters)z20X OKz8AssertionError: Status message must begin w/3-digit code)Z200OKz;AssertionError: Status message must have a space after coderp   rh   ri   )subTestrH   rk   rl   rZ   ra   )r   rr   Ztestsrq   Zexc_messagerF   rG   r   r   r   test_status_validation_errors   s    z.IntegrationTests.test_status_validation_errorsc                 C   s@   dd }t t|\}}| |d | | d d d S )Nc                 S   s   | d    |ddg dgS )N
wsgi.inputr,   ro      data)readesr   r   r   rg      s    z1IntegrationTests.test_wsgi_input.<locals>.bad_apprh   ri   rJ   rj   rm   r   r   r   test_wsgi_input   s    z IntegrationTests.test_wsgi_inputc                 C   sl   dd }t t|\}}| |d tj d d}t d}|d | }| 	d| d | d S )	Nc                 S   s   |dddg dgS )Nr,   ro   r0   zWed, 24 Dec 2008 13:29:32 GMTrv   r   rx   r   r   r   rB      s
    z3IntegrationTests.test_bytes_validation.<locals>.appz"GET / HTTP/1.0" 200 4
r   ascii   /s(   HTTP/1.0 200 OK
Server: WSGIServer/0.2 sV   
Content-Type: text/plain; charset=utf-8
Date: Wed, 24 Dec 2008 13:29:32 GMT

data)
rH   r   rk   rl   r?   rX   rY   r:   r   rZ   )r   rB   rF   rG   verpyr\   r   r   r   test_bytes_validation   s    z&IntegrationTests.test_bytes_validationc                 C   s>   dd }t t|dd\}}| dtjdddd	g|  d S )
Nc                 S   s   |dddg | d  dgS )Nr,   r-   r|   r7   latin1r:   rx   r   r   r   rB      s
    z-IntegrationTests.test_cp1252_url.<locals>.apps   GET /%80 HTTP/1.0rd   s   HTTP/1.0 200 OKs   Content-Type: text/plains#   Date: Wed, 24 Dec 2008 13:29:32 GMT    s   /)rH   r   rZ   r   ANYra   )r   rB   rF   rG   r   r   r   test_cp1252_url   s    	
z IntegrationTests.test_cp1252_urlc                    s   t tddd }G dd dtt}ttjd||d| j	 t
   fdd	}ttj|}| tjtj| d t
  fd
d}t
j|d}|    |  | t jd  d S )Npthread_killc                 S   s   |dg  dt j gS )Nr,       )r   SOCK_MAX_SIZEr2   r   r   r   rB     s    
z4IntegrationTests.test_interrupted_write.<locals>.appc                   @   s   e Zd ZdS )z<IntegrationTests.test_interrupted_write.<locals>.WsgiHandlerNr"   r#   r$   r   r   r   r   WsgiHandler  s   r   r   )Zhandler_classc                    s       d S r   )set)signumframe)interruptedr   r   signal_handler  s    z?IntegrationTests.test_interrupted_write.<locals>.signal_handlerc                     s   t j } | dd |  F}|d tj  jtddr*qJq*t	| W d    n1 sj0    Y  | 
  d S )NGETrW   d   rI   )timeout)r   r   r'   Zgetresponserw   signalSIGUSR1waitfloatlenclose)httpresponser   main_threadr   ZreceivedrD   r   r   
run_client  s    


*z;IntegrationTests.test_interrupted_write.<locals>.run_client)targetr   )r   Zget_attributer   r   r   r   r   ZHOSTZ
addCleanupZserver_close	threadingEventr   	get_identThreadstartZhandle_requestr9   rZ   r   )r   rB   r   r   Zoriginalr   Z
backgroundr   r   r   test_interrupted_write   s"    z'IntegrationTests.test_interrupted_writeN)T)r"   r#   r$   r]   r_   rb   re   rf   rn   rt   r{   r   r   r   r   r   r   r   rV   x   s   
rV   c                   @   s   e Zd Zdd Zd$ddZdd Zdd	 Zd%ddZej	e
ddd Zdd Zdd Zdd Zdd Zdd Zdd Zdd Zdd Zd d! Zd"d# ZdS )&UtilityTestsc                 C   sJ   ||d}t | | t || | |d | | |d | |S )NSCRIPT_NAMEr7   r7   r   )r   r   rZ   Zshift_path_info)r   Zsn_inZpi_inpartZsn_outZpi_outenvr   r   r   
checkShift2  s    

zUtilityTests.checkShiftNc                 C   s|   i }t | t|tr*| || t n,t|trF| || t n| || | ||i}t | | || | d S r   )r   r   
isinstancer   ZassertIsInstancer   rZ   ZassertIs)r   keyvaluealtr   r   r   r   checkDefault:  s    



zUtilityTests.checkDefaultc                 K   s   t | | || | d S r   )r   r   rZ   )r   r   r   kwr   r   r   checkCrossDefaultJ  s    
zUtilityTests.checkCrossDefaultc                 K   s    t | | t || d S r   )r   r   rZ   Zapplication_uri)r   urir   r   r   r   checkAppURIN  s    
zUtilityTests.checkAppURIrI   c                 K   s"   t | | t ||| d S r   )r   r   rZ   Zrequest_uri)r   r   queryr   r   r   r   checkReqURIR  s    
zUtilityTests.checkReqURI)categoryc                 C   s^   ||fdd}t || | }| |jj |D ]}q0| |jj |  | |jj d S )Nc                 S   s   t t| |S r   )r   FileWrapperr   )textsizer   r   r   rP   Y  s    z%UtilityTests.checkFW.<locals>.make_it)rU   assertFalseZfilelikeclosedr   rk   )r   r   r   rQ   rP   rR   rT   r   r   r   checkFWV  s    
zUtilityTests.checkFWc                 C   sP   t tdd}| td  | |d d W d    n1 sB0    Y  d S )NZfoobar   zUse iterator protocol insteadrI   foo)r   r   r   assertWarnsRegexDeprecationWarningrZ   )r   wrapperr   r   r   $test_filewrapper_getitem_deprecationi  s
    z1UtilityTests.test_filewrapper_getitem_deprecationc                 C   s^   |  ddddd |  ddddd |  ddd dd |  ddddd |  dd	ddd d S )
Nr<   rW   z/xx/az/x/yz/a/x/yz/x/r   r)   r   r   r   testSimpleShiftsp  s
    zUtilityTests.testSimpleShiftsc                 C   s   |  ddddd |  ddddd |  dddd	d |  dd
dd	d |  dddd	d |  dddd	d |  ddddd |  ddddd |  ddddd |  ddddd |  ddd dd d S )Nz/a/bz/../yz..r   r   r<   z//yyz/a/b/yz//y/rW   z/./yz/./y/z///./..//y/.//z/y/z///z/a/b/z/.//z/x//r   z/a/b/xz/.r   r)   r   r   r   testNormalizedShiftsw  s    z!UtilityTests.testNormalizedShiftsc                 C   sF   ddddddddd	d
ddt  fdt fdfD ]\}}| || q,d S )N)SERVER_NAMEr>   )SERVER_PORT80)SERVER_PROTOCOLHTTP/1.0)	HTTP_HOSTr>   )ZREQUEST_METHODr   )r   r<   )r7   rW   )wsgi.versionrI   r   )wsgi.run_oncer   )wsgi.multithreadr   )wsgi.multiprocessr   ru   wsgi.errors)wsgi.url_schemer   )r   r   r   )r   r   r   r   r   r   testDefaults  s     zUtilityTests.testDefaultsc                 C   st   | j dddd | j dddd | j dddd | j ddd	d | j dd
dd | j dddd | j dddd d S )Nr   zfoo.barr   r   httpsonHTTPS1yesr   r   r   r   Z443)r   r)   r   r   r   testCrossDefaults  s    zUtilityTests.testCrossDefaultsc                 C   sn   |  ti d |  tddid |  tddid |  tddid |  tddid d S )Nr   r   r   r   r   r   r   )rZ   r   Zguess_schemer)   r   r   r   testGuessScheme  s
    zUtilityTests.testGuessSchemec                 C   sv   |  d | j ddd | j ddd | j ddd	d
 | j ddd | j dddd | j ddd | j ddd d d S )Nhttp://127.0.0.1/http://127.0.0.1/spam/spamr   http://127.0.0.1/sp%E4m   /spämzhttp://spam.example.com:2071/zspam.example.com:2071Z2071)r   r   zhttp://spam.example.com/zspam.example.comr   r>   )r   r   zhttps://127.0.0.1/r   r   zhttp://127.0.0.1:8000/Z8000)r   r   )r   r)   r   r   r   testAppURIs  s     
zUtilityTests.testAppURIsc                 C   s   |  d | j ddd | j ddd | j dddd	 | j d
ddd	 | j dddd	 | j dddd	 | j ddddd | j ddddd | j dddddd d S )Nr   r   r   r   r   r   zhttp://127.0.0.1/spammity/spamz	/spammityr   z http://127.0.0.1/spammity/sp%E4mz"http://127.0.0.1/spammity/spam;hamz	/spam;hamz/http://127.0.0.1/spammity/spam;cookie=1234,5678z/spam;cookie=1234,5678z%http://127.0.0.1/spammity/spam?say=nizsay=ni)r   r7   r6   z'http://127.0.0.1/spammity/spam?s%E4y=nizs%E4y=nir   )r   r)   r   r   r   testReqURIs  s0    
zUtilityTests.testReqURIsc                 C   s   |  ddddg d S )NZxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzx   ZxxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzxyzZxyzxyzxyzxyzxyzxyzxyzxyzxyzxyz)r   r)   r   r   r   testFileWrapper  s    zUtilityTests.testFileWrapperc                 C   s|   d  D ]2}|| | | fD ]}| t| q$qd  D ]2}|| | | fD ]}| t| q`qDd S )NzbConnection Keep-Alive Proxy-Authenticate Proxy-Authorization TE Trailers Transfer-Encoding Upgradez4Accept Cache-Control Date Pragma Trailer Via Warning)rY   titleupperlowerrk   r   Zis_hop_by_hopr   )r   Zhopr   r   r   r   testHopByHop  s    

zUtilityTests.testHopByHop)N)rI   )r"   r#   r$   r   r   r   r   r   r   Zignore_warningsr   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   0  s"   



	r   c                   @   s$   e Zd Zdd Zdd Zdd ZdS )HeaderTestsc                 C   s  dg}|  tt d |  ttg d |  tt|d d  d |  t|d d   dg |  t|d d   dg |  t|d d   | | t| | t }|d= d|d< |j|j|j	|j
fD ]<}| |d | |d | |d	 | |d q|  |d d d
|d< |  |d	 d
 |  |	dd
g |  |ddd
 |  |ddd |  |ddd
 |  |ddd |  |d d
 |  |d d d S )N)r   r   r   rI   r   r   r   barFooZFOObazZwheeZzoo)rZ   r   r   keysvaluesitemsZassertIsNot__contains__getget_all__getitem__rk   r   
setdefault)r   testhmr   r   r   testMappingInterface  s4    z HeaderTests.testMappingInterfacec                 C   s   |  ttd d S )Nr   )assertRaises	TypeErrorr   r)   r   r   r   testRequireList  s    zHeaderTests.testRequireListc                 C   s   t  }| t|d |jdddd | |d d | t|d |jddd d	 | |ddd
g | t|d d S )Nz
r   r   Zspam)r   zbar; baz="spam"zfoo: bar; baz="spam"

r   )Zcheesezbar; cheesez*foo: bar; baz="spam"
Foo: bar; cheese

)r   rZ   strZ
add_headerr   r   r   r   r   r   
testExtras  s    
zHeaderTests.testExtrasN)r"   r#   r$   r   r  r  r   r   r   r   r     s    r   c                   @   s&   e Zd ZdZeej Zdd Z	dS )ErrorHandlerz/Simple handler subclass for testing BaseHandlerc              	   K   s*   t | tj| t t t |ddd d S )NT)multithreadmultiprocess)r   r
   r   r   r   )r   r   r   r   r   r     s
    zErrorHandler.__init__N)
r"   r#   r$   r%   dictosr3   r   
os_environr   r   r   r   r   r    s   r  c                   @   s   e Zd ZdZdd ZdS )TestHandlerzASimple handler subclass for testing BaseHandler, w/error passthruc                  C   s    d S r   r   r)   r   r   r   handle_error#  s    zTestHandler.handle_errorN)r"   r#   r$   r%   r  r   r   r   r   r     s   r  c                   @   sx   e Zd ZdZdd Zdd Zdd Zdd	 Zd
d Zdd Z	dd Z
dd Zdd Zdd Zdd Zdd Zdd ZdS )HandlerTestsi  c                 C   s   dddddd}t td|$ tdd	d
}|  W d    n1 sH0    Y  dD ]$}| t|d| |jd|   qVi }t| | D ]\}}||vr|||< q|	dd	dd|
 | dddddtjd | |j| d S )Nz/my/homez/my/pathzfr_FR.UTF-8Ztest_script_nameZtest_server_name)HOMEPATHLANGr   r   r  Yz/override/home)Xr  )rX   r  r  Zrun_onceZfile_wrapperZwsgi_zwsgi.r<   r>   r   Fr   T)r  r  r   r   ru   r   r   r   r   r   r   zwsgi.file_wrapper)r   Z	swap_attrr  r   rZ   getattrr3   r   r   update	get_stdin
get_stderrr   r   ZassertDictEqual)r   r  handlerattrZexpectedr   r   r   r   r   testEnviron+  sB    &
zHandlerTests.testEnvironc                 C   s2   t d d d i }|  dD ]}| ||j qd S )N)r   ru   r   )r
   r   assertInr3   )r   r   r   r   r   r   testCGIEnvirona  s    zHandlerTests.testCGIEnvironc                 C   sH   t dd}|  | |jd d t  }|  | |jd d d S )Nr   r   r   r   r   )r  r   rZ   r3   r  r   r   r   
testSchemeg  s    zHandlerTests.testSchemec                 C   s6   t  }dD ]}| tt|| q
| t|jd d S )N)Z_flushr  r  Zadd_cgi_varsr   )r	   r   NotImplementedErrorr  _write)r   r   namer   r   r   testAbstractMethodsm  s    z HandlerTests.testAbstractMethodsc                 C   s   dd }dd }dd }dd }t  }|| | |j d	d
 t  }|| | |j dd
 t  }|| | |j d t  }|| | |j d d S )Nc                 S   s   |dg  | d  dgS Nr,   r   r8   r   rx   r   r   r   trivial_app1x  s    
z4HandlerTests.testContentLength.<locals>.trivial_app1c                 S   s   |dg | d  d g S r"  r   rx   r   r   r   trivial_app2|  s    z4HandlerTests.testContentLength.<locals>.trivial_app2c                 S   s   |dg  d dgS )Nr,   u   тестzutf-8r   rx   r   r   r   trivial_app3  s    
z4HandlerTests.testContentLength.<locals>.trivial_app3c                 S   s   |ddg g S )Nr,   )zContent-LengthZ12345r   rx   r   r   r   trivial_app4  s    z4HandlerTests.testContentLength.<locals>.trivial_app4z)Status: 200 OK
Content-Length: 4

httpr8   zStatus: 200 OK

https-   Status: 200 OK
Content-Length: 8

тестs)   Status: 200 OK
Content-Length: 12345

)r  runrZ   stdoutrA   r:   )r   r#  r$  r%  r&  r   r   r   r   testContentLengthu  s8    



zHandlerTests.testContentLengthc                 C   s   dd }dd }t  }|| | |j dd | |j d t  }|| | |j d|jt|j	f d|j	  | 
d	|j  d S )
Nc                 S   s   |dg  g S Nr,   r   rx   r   r   r   non_error_app  s    
z8HandlerTests.testBasicErrorOutput.<locals>.non_error_appc                 S   s   t dd S )N This should be caught by handlerrJ   rx   r   r   r   	error_app  s    z4HandlerTests.testBasicErrorOutput.<locals>.error_app%Status: 200 OK
Content-Length: 0

r8   r<   z<Status: %s
Content-Type: text/plain
Content-Length: %d

rJ   )r  r'  rZ   r(  rA   r:   r@   Zerror_statusr   Z
error_bodyr  )r   r+  r.  r   r   r   r   testBasicErrorOutput  s,    

z!HandlerTests.testBasicErrorOutputc                    sR   d  fdd}t  }|| | |j dd   | d|j  d S )N   Some output has been sentc                    s   |dg   t dd S )Nr,   r,  r-  rx   MSGr   r   r.    s    z4HandlerTests.testErrorAfterOutput.<locals>.error_appzStatus: 200 OK

r8   rJ   )r  r'  rZ   r(  rA   r:   r  r@   r   r.  r   r   r2  r   testErrorAfterOutput  s    
z!HandlerTests.testErrorAfterOutputc           	   
   C   s  dd }d}d d}dD ]}|r*d| p,d}d	D ]}d
D ]}t|d}d|_||_||_|| | ||j  t|d}d|_||_||_|| |dkr| |j d q:| 	t
|||f  d|j |||f  d|j f q:q2qd S )Nc                 S   s   |dg  g S r*  r   rx   r   r   r   r+    s    
z5HandlerTests.testHeaderFormats.<locals>.non_error_appzfHTTP/%s 200 OK\r\nDate: \w{3}, [ 0123]\d \w{3} \d{4} \d\d:\d\d:\d\d GMT\r\n%sContent-Length: 0\r\n\r\nr/  r8   )z
FooBar/1.0NzServer: %s
r<   )z1.0z1.1)HTTP/0.9r   zHTTP/1.1)r   FTr6  r   )r:   r  Zorigin_serverZhttp_versionZserver_softwarer'  rZ   r(  rA   rk   rerQ   )	r   r+  ZstdpatZshortpatZsswswrX   protor   r   r   r   testHeaderFormats  s@    



zHandlerTests.testHeaderFormatsc                 C   s.   dd }t  }|| | d|j  d S )Nc                 S   s   |ddg dgS )Nr,   ro   rv   r   rx   r   r   r   rB     s    z'HandlerTests.testBytesData.<locals>.appsR   Status: 200 OK
Content-Type: text/plain; charset=utf-8
Content-Length: 4

data)r  r'  rZ   r(  rA   )r   rB   r   r   r   r   testBytesData  s    
zHandlerTests.testBytesDatac                    s>   ddid  fdd}t  }|| | d d d S )Nclose_calledFr1  c                    s(   |dg   G fdddt }| S )Nr,   c                       s    e Zd Zdd Z fddZdS )zHHandlerTests.testCloseOnError.<locals>.error_app.<locals>.CrashyIterablec                 s   s   dV  t dq d S )Ns   blahr,  r-  r)   r   r   r   __iter__  s    zQHandlerTests.testCloseOnError.<locals>.error_app.<locals>.CrashyIterable.__iter__c                    s   d d< d S )NTr<  r   r)   side_effectsr   r   r     s    zNHandlerTests.testCloseOnError.<locals>.error_app.<locals>.CrashyIterable.closeN)r"   r#   r$   r=  r   r   r>  r   r   CrashyIterable  s   r@  )object)ry   rz   r@  r3  r?  r   r   r.    s    z0HandlerTests.testCloseOnError.<locals>.error_appT)r  r'  rZ   r4  r   rB  r   testCloseOnError  s    
zHandlerTests.testCloseOnErrorc                    s~   t   G  fddd}ddi}tt | tj|}d}| t| |t W d    n1 sd0    Y  | 	d  d S )Nc                       s    e Zd Z fddZdd ZdS )z4HandlerTests.testPartialWrite.<locals>.PartialWriterc                    s   |d d }  | t|S )N   )extendr   )r   bpartialZwrittenr   r   write!  s    
z:HandlerTests.testPartialWrite.<locals>.PartialWriter.writec                 S   s   d S r   r   r)   r   r   r   flush&  s    z:HandlerTests.testPartialWrite.<locals>.PartialWriter.flushN)r"   r#   r$   rI  rJ  r   rH  r   r   PartialWriter   s   rK  r   r   zshould not do partial writesss   HTTP/1.0 200 OK
Content-Type: text/plain
Date: Mon, 05 Jun 2006 18:49:54 GMT
Content-Length: 13

Hello, world!)
	bytearrayr   r   r?   r@   r   r   r'  r4   rZ   )r   rK  r3   r   msgr   rH  r   testPartialWrite  s    	(zHandlerTests.testPartialWritec              	      s   ddi}t ttfD ]r | j dR G  fddd}t }tt | ||}|t | 	|
  W d    q1 sz0    Y  qd S )Nr   r   	exceptionc                       s   e Zd Z fddZdS )zEHandlerTests.testClientConnectionTerminations.<locals>.AbortingWriterc                    s    d S r   r   r   rF  rO  r   r   rI  ?  s    zKHandlerTests.testClientConnectionTerminations.<locals>.AbortingWriter.writeNr"   r#   r$   rI  r   rO  r   r   AbortingWriter>  s   rS  )ConnectionAbortedErrorBrokenPipeErrorConnectionResetErrorrs   r   r   r   r'  r4   r   rA   )r   r3   rS  r@   r   r   rO  r    testClientConnectionTerminations6  s    
z-HandlerTests.testClientConnectionTerminationsc                    s   G dd dt  G  fddd}t }ddi}tt | ||}|t | d|  | |j	 | |j
 | |j | |j d S )Nc                   @   s   e Zd ZdS )zKHandlerTests.testDontResetInternalStateOnException.<locals>.CustomExceptionNr   r   r   r   r   CustomExceptionI  s   rX  c                       s   e Zd Z fddZdS )zJHandlerTests.testDontResetInternalStateOnException.<locals>.AbortingWriterc                    s    d S r   r   rQ  rX  r   r   rI  Q  s    zPHandlerTests.testDontResetInternalStateOnException.<locals>.AbortingWriter.writeNrR  r   rY  r   r   rS  P  s   rS  r   r   )
ValueErrorr   r   r   r'  r4   r  rA   ZassertIsNotNoneresultZheadersrq   r3   )r   rS  r@   r3   r   r   rY  r   %testDontResetInternalStateOnExceptionH  s    
z2HandlerTests.testDontResetInternalStateOnExceptionN)r"   r#   r$   ZmaxDiffr  r  r  r!  r)  r0  r5  r:  r;  rC  rN  rW  r\  r   r   r   r   r  '  s   62+r  __main__)6Zunittestr   r   r   Ztest.supportr   Ztest.test_httpserversr   r   Zwsgiref.utilr   Zwsgiref.headersr   Zwsgiref.handlersr	   r
   r   Zwsgirefr   Zwsgiref.validater   Zwsgiref.simple_serverr   r   r   Zhttp.clientr   ior   r   r   socketserverr   platformr   r
  r7  r   r?   r   r   r&   r4   r;   rH   rU   rV   r   r   r  r  r  r"   mainr   r   r   r   <module>   sN   
% 9 +7  =
