1*1596Szelenkov@nginx.comimport pytest 21274Szelenkov@nginx.comimport re 31477Szelenkov@nginx.comimport socket 41274Szelenkov@nginx.comimport time 51477Szelenkov@nginx.com 61274Szelenkov@nginx.comfrom unit.applications.lang.python import TestApplicationPython 7*1596Szelenkov@nginx.comfrom conftest import option, skip_alert 81274Szelenkov@nginx.com 91274Szelenkov@nginx.com 101274Szelenkov@nginx.comclass TestProxy(TestApplicationPython): 111467Szelenkov@nginx.com prerequisites = {'modules': {'python': 'any'}} 121274Szelenkov@nginx.com 131274Szelenkov@nginx.com SERVER_PORT = 7999 141274Szelenkov@nginx.com 151353Smax.romanov@nginx.com @staticmethod 161353Smax.romanov@nginx.com def run_server(server_port): 171274Szelenkov@nginx.com sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM) 181274Szelenkov@nginx.com sock.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1) 191274Szelenkov@nginx.com 201353Smax.romanov@nginx.com server_address = ('', server_port) 211274Szelenkov@nginx.com sock.bind(server_address) 221274Szelenkov@nginx.com sock.listen(5) 231274Szelenkov@nginx.com 241274Szelenkov@nginx.com def recvall(sock): 251274Szelenkov@nginx.com buff_size = 4096 261274Szelenkov@nginx.com data = b'' 271274Szelenkov@nginx.com while True: 281274Szelenkov@nginx.com part = sock.recv(buff_size) 291274Szelenkov@nginx.com data += part 301274Szelenkov@nginx.com if len(part) < buff_size: 311274Szelenkov@nginx.com break 321274Szelenkov@nginx.com return data 331274Szelenkov@nginx.com 341274Szelenkov@nginx.com req = b"""HTTP/1.1 200 OK 351274Szelenkov@nginx.comContent-Length: 10 361274Szelenkov@nginx.com 371274Szelenkov@nginx.com""" 381274Szelenkov@nginx.com 391274Szelenkov@nginx.com while True: 401274Szelenkov@nginx.com connection, client_address = sock.accept() 411274Szelenkov@nginx.com 421274Szelenkov@nginx.com data = recvall(connection).decode() 431274Szelenkov@nginx.com 441274Szelenkov@nginx.com to_send = req 451274Szelenkov@nginx.com 46*1596Szelenkov@nginx.com m = re.search(r'X-Len: (\d+)', data) 471274Szelenkov@nginx.com if m: 481274Szelenkov@nginx.com to_send += b'X' * int(m.group(1)) 491274Szelenkov@nginx.com 501274Szelenkov@nginx.com connection.sendall(to_send) 511274Szelenkov@nginx.com 521274Szelenkov@nginx.com connection.close() 531274Szelenkov@nginx.com 541274Szelenkov@nginx.com def get_http10(self, *args, **kwargs): 551274Szelenkov@nginx.com return self.get(*args, http_10=True, **kwargs) 561274Szelenkov@nginx.com 571274Szelenkov@nginx.com def post_http10(self, *args, **kwargs): 581274Szelenkov@nginx.com return self.post(*args, http_10=True, **kwargs) 591274Szelenkov@nginx.com 60*1596Szelenkov@nginx.com def setup_method(self): 61*1596Szelenkov@nginx.com super().setup_method() 621274Szelenkov@nginx.com 631353Smax.romanov@nginx.com self.run_process(self.run_server, self.SERVER_PORT) 641274Szelenkov@nginx.com self.waitforsocket(self.SERVER_PORT) 651274Szelenkov@nginx.com 66*1596Szelenkov@nginx.com assert 'success' in self.conf( 67*1596Szelenkov@nginx.com { 68*1596Szelenkov@nginx.com "listeners": { 69*1596Szelenkov@nginx.com "*:7080": {"pass": "routes"}, 70*1596Szelenkov@nginx.com "*:7081": {"pass": "applications/mirror"}, 71*1596Szelenkov@nginx.com }, 72*1596Szelenkov@nginx.com "routes": [{"action": {"proxy": "http://127.0.0.1:7081"}}], 73*1596Szelenkov@nginx.com "applications": { 74*1596Szelenkov@nginx.com "mirror": { 75*1596Szelenkov@nginx.com "type": "python", 76*1596Szelenkov@nginx.com "processes": {"spare": 0}, 77*1596Szelenkov@nginx.com "path": option.test_dir + "/python/mirror", 78*1596Szelenkov@nginx.com "working_directory": option.test_dir 79*1596Szelenkov@nginx.com + "/python/mirror", 80*1596Szelenkov@nginx.com "module": "wsgi", 811274Szelenkov@nginx.com }, 82*1596Szelenkov@nginx.com "custom_header": { 83*1596Szelenkov@nginx.com "type": "python", 84*1596Szelenkov@nginx.com "processes": {"spare": 0}, 85*1596Szelenkov@nginx.com "path": option.test_dir + "/python/custom_header", 86*1596Szelenkov@nginx.com "working_directory": option.test_dir 87*1596Szelenkov@nginx.com + "/python/custom_header", 88*1596Szelenkov@nginx.com "module": "wsgi", 891274Szelenkov@nginx.com }, 90*1596Szelenkov@nginx.com "delayed": { 91*1596Szelenkov@nginx.com "type": "python", 92*1596Szelenkov@nginx.com "processes": {"spare": 0}, 93*1596Szelenkov@nginx.com "path": option.test_dir + "/python/delayed", 94*1596Szelenkov@nginx.com "working_directory": option.test_dir 95*1596Szelenkov@nginx.com + "/python/delayed", 96*1596Szelenkov@nginx.com "module": "wsgi", 97*1596Szelenkov@nginx.com }, 98*1596Szelenkov@nginx.com }, 99*1596Szelenkov@nginx.com } 100*1596Szelenkov@nginx.com ), 'proxy initial configuration' 1011274Szelenkov@nginx.com 1021274Szelenkov@nginx.com def test_proxy_http10(self): 1031274Szelenkov@nginx.com for _ in range(10): 104*1596Szelenkov@nginx.com assert self.get_http10()['status'] == 200, 'status' 1051274Szelenkov@nginx.com 1061274Szelenkov@nginx.com def test_proxy_chain(self): 107*1596Szelenkov@nginx.com assert 'success' in self.conf( 108*1596Szelenkov@nginx.com { 109*1596Szelenkov@nginx.com "listeners": { 110*1596Szelenkov@nginx.com "*:7080": {"pass": "routes/first"}, 111*1596Szelenkov@nginx.com "*:7081": {"pass": "routes/second"}, 112*1596Szelenkov@nginx.com "*:7082": {"pass": "routes/third"}, 113*1596Szelenkov@nginx.com "*:7083": {"pass": "routes/fourth"}, 114*1596Szelenkov@nginx.com "*:7084": {"pass": "routes/fifth"}, 115*1596Szelenkov@nginx.com "*:7085": {"pass": "applications/mirror"}, 116*1596Szelenkov@nginx.com }, 117*1596Szelenkov@nginx.com "routes": { 118*1596Szelenkov@nginx.com "first": [{"action": {"proxy": "http://127.0.0.1:7081"}}], 119*1596Szelenkov@nginx.com "second": [{"action": {"proxy": "http://127.0.0.1:7082"}}], 120*1596Szelenkov@nginx.com "third": [{"action": {"proxy": "http://127.0.0.1:7083"}}], 121*1596Szelenkov@nginx.com "fourth": [{"action": {"proxy": "http://127.0.0.1:7084"}}], 122*1596Szelenkov@nginx.com "fifth": [{"action": {"proxy": "http://127.0.0.1:7085"}}], 123*1596Szelenkov@nginx.com }, 124*1596Szelenkov@nginx.com "applications": { 125*1596Szelenkov@nginx.com "mirror": { 126*1596Szelenkov@nginx.com "type": "python", 127*1596Szelenkov@nginx.com "processes": {"spare": 0}, 128*1596Szelenkov@nginx.com "path": option.test_dir + "/python/mirror", 129*1596Szelenkov@nginx.com "working_directory": option.test_dir 130*1596Szelenkov@nginx.com + "/python/mirror", 131*1596Szelenkov@nginx.com "module": "wsgi", 132*1596Szelenkov@nginx.com } 133*1596Szelenkov@nginx.com }, 134*1596Szelenkov@nginx.com } 135*1596Szelenkov@nginx.com ), 'proxy chain configuration' 1361274Szelenkov@nginx.com 137*1596Szelenkov@nginx.com assert self.get_http10()['status'] == 200, 'status' 1381274Szelenkov@nginx.com 1391274Szelenkov@nginx.com def test_proxy_body(self): 1401274Szelenkov@nginx.com payload = '0123456789' 1411274Szelenkov@nginx.com for _ in range(10): 1421274Szelenkov@nginx.com resp = self.post_http10(body=payload) 1431274Szelenkov@nginx.com 144*1596Szelenkov@nginx.com assert resp['status'] == 200, 'status' 145*1596Szelenkov@nginx.com assert resp['body'] == payload, 'body' 1461274Szelenkov@nginx.com 1471274Szelenkov@nginx.com payload = 'X' * 4096 1481274Szelenkov@nginx.com for _ in range(10): 1491274Szelenkov@nginx.com resp = self.post_http10(body=payload) 1501274Szelenkov@nginx.com 151*1596Szelenkov@nginx.com assert resp['status'] == 200, 'status' 152*1596Szelenkov@nginx.com assert resp['body'] == payload, 'body' 1531274Szelenkov@nginx.com 1541274Szelenkov@nginx.com payload = 'X' * 4097 1551274Szelenkov@nginx.com for _ in range(10): 1561274Szelenkov@nginx.com resp = self.post_http10(body=payload) 1571274Szelenkov@nginx.com 158*1596Szelenkov@nginx.com assert resp['status'] == 200, 'status' 159*1596Szelenkov@nginx.com assert resp['body'] == payload, 'body' 1601274Szelenkov@nginx.com 1611274Szelenkov@nginx.com payload = 'X' * 4096 * 256 1621274Szelenkov@nginx.com for _ in range(10): 1631274Szelenkov@nginx.com resp = self.post_http10(body=payload, read_buffer_size=4096 * 128) 1641274Szelenkov@nginx.com 165*1596Szelenkov@nginx.com assert resp['status'] == 200, 'status' 166*1596Szelenkov@nginx.com assert resp['body'] == payload, 'body' 1671274Szelenkov@nginx.com 1681274Szelenkov@nginx.com payload = 'X' * 4096 * 257 1691274Szelenkov@nginx.com for _ in range(10): 1701274Szelenkov@nginx.com resp = self.post_http10(body=payload, read_buffer_size=4096 * 128) 1711274Szelenkov@nginx.com 172*1596Szelenkov@nginx.com assert resp['status'] == 200, 'status' 173*1596Szelenkov@nginx.com assert resp['body'] == payload, 'body' 1741274Szelenkov@nginx.com 1751366Szelenkov@nginx.com self.conf({'http': {'max_body_size': 32 * 1024 * 1024}}, 'settings') 1761366Szelenkov@nginx.com 1771366Szelenkov@nginx.com payload = '0123456789abcdef' * 32 * 64 * 1024 1781366Szelenkov@nginx.com resp = self.post_http10(body=payload, read_buffer_size=1024 * 1024) 179*1596Szelenkov@nginx.com assert resp['status'] == 200, 'status' 180*1596Szelenkov@nginx.com assert resp['body'] == payload, 'body' 1811366Szelenkov@nginx.com 1821274Szelenkov@nginx.com def test_proxy_parallel(self): 1831274Szelenkov@nginx.com payload = 'X' * 4096 * 257 1841274Szelenkov@nginx.com buff_size = 4096 * 258 1851274Szelenkov@nginx.com 1861274Szelenkov@nginx.com socks = [] 1871274Szelenkov@nginx.com for i in range(10): 1881274Szelenkov@nginx.com _, sock = self.post_http10( 1891274Szelenkov@nginx.com body=payload + str(i), 1901274Szelenkov@nginx.com start=True, 1911274Szelenkov@nginx.com no_recv=True, 1921274Szelenkov@nginx.com read_buffer_size=buff_size, 1931274Szelenkov@nginx.com ) 1941274Szelenkov@nginx.com socks.append(sock) 1951274Szelenkov@nginx.com 1961274Szelenkov@nginx.com for i in range(10): 1971274Szelenkov@nginx.com resp = self.recvall(socks[i], buff_size=buff_size).decode() 1981274Szelenkov@nginx.com socks[i].close() 1991274Szelenkov@nginx.com 2001274Szelenkov@nginx.com resp = self._resp_to_dict(resp) 2011274Szelenkov@nginx.com 202*1596Szelenkov@nginx.com assert resp['status'] == 200, 'status' 203*1596Szelenkov@nginx.com assert resp['body'] == payload + str(i), 'body' 2041274Szelenkov@nginx.com 2051274Szelenkov@nginx.com def test_proxy_header(self): 206*1596Szelenkov@nginx.com assert 'success' in self.conf( 207*1596Szelenkov@nginx.com {"pass": "applications/custom_header"}, 'listeners/*:7081' 208*1596Szelenkov@nginx.com ), 'custom_header configure' 2091274Szelenkov@nginx.com 2101274Szelenkov@nginx.com header_value = 'blah' 211*1596Szelenkov@nginx.com assert ( 2121274Szelenkov@nginx.com self.get_http10( 2131274Szelenkov@nginx.com headers={'Host': 'localhost', 'Custom-Header': header_value} 214*1596Szelenkov@nginx.com )['headers']['Custom-Header'] 215*1596Szelenkov@nginx.com == header_value 216*1596Szelenkov@nginx.com ), 'custom header' 2171274Szelenkov@nginx.com 2181274Szelenkov@nginx.com header_value = '(),/:;<=>?@[\]{}\t !#$%&\'*+-.^_`|~' 219*1596Szelenkov@nginx.com assert ( 2201274Szelenkov@nginx.com self.get_http10( 2211274Szelenkov@nginx.com headers={'Host': 'localhost', 'Custom-Header': header_value} 222*1596Szelenkov@nginx.com )['headers']['Custom-Header'] 223*1596Szelenkov@nginx.com == header_value 224*1596Szelenkov@nginx.com ), 'custom header 2' 2251274Szelenkov@nginx.com 2261274Szelenkov@nginx.com header_value = 'X' * 4096 227*1596Szelenkov@nginx.com assert ( 2281274Szelenkov@nginx.com self.get_http10( 2291274Szelenkov@nginx.com headers={'Host': 'localhost', 'Custom-Header': header_value} 230*1596Szelenkov@nginx.com )['headers']['Custom-Header'] 231*1596Szelenkov@nginx.com == header_value 232*1596Szelenkov@nginx.com ), 'custom header 3' 2331274Szelenkov@nginx.com 2341274Szelenkov@nginx.com header_value = 'X' * 8191 235*1596Szelenkov@nginx.com assert ( 2361274Szelenkov@nginx.com self.get_http10( 2371274Szelenkov@nginx.com headers={'Host': 'localhost', 'Custom-Header': header_value} 238*1596Szelenkov@nginx.com )['headers']['Custom-Header'] 239*1596Szelenkov@nginx.com == header_value 240*1596Szelenkov@nginx.com ), 'custom header 4' 2411274Szelenkov@nginx.com 2421274Szelenkov@nginx.com header_value = 'X' * 8192 243*1596Szelenkov@nginx.com assert ( 2441274Szelenkov@nginx.com self.get_http10( 2451274Szelenkov@nginx.com headers={'Host': 'localhost', 'Custom-Header': header_value} 246*1596Szelenkov@nginx.com )['status'] 247*1596Szelenkov@nginx.com == 431 248*1596Szelenkov@nginx.com ), 'custom header 5' 2491274Szelenkov@nginx.com 2501274Szelenkov@nginx.com def test_proxy_fragmented(self): 2511274Szelenkov@nginx.com _, sock = self.http( 2521274Szelenkov@nginx.com b"""GET / HTT""", raw=True, start=True, no_recv=True 2531274Szelenkov@nginx.com ) 2541274Szelenkov@nginx.com 2551274Szelenkov@nginx.com time.sleep(1) 2561274Szelenkov@nginx.com 2571274Szelenkov@nginx.com sock.sendall("P/1.0\r\nHost: localhos".encode()) 2581274Szelenkov@nginx.com 2591274Szelenkov@nginx.com time.sleep(1) 2601274Szelenkov@nginx.com 2611274Szelenkov@nginx.com sock.sendall("t\r\n\r\n".encode()) 2621274Szelenkov@nginx.com 263*1596Szelenkov@nginx.com assert re.search( 264*1596Szelenkov@nginx.com '200 OK', self.recvall(sock).decode() 265*1596Szelenkov@nginx.com ), 'fragmented send' 2661274Szelenkov@nginx.com sock.close() 2671274Szelenkov@nginx.com 2681274Szelenkov@nginx.com def test_proxy_fragmented_close(self): 2691274Szelenkov@nginx.com _, sock = self.http( 2701274Szelenkov@nginx.com b"""GET / HTT""", raw=True, start=True, no_recv=True 2711274Szelenkov@nginx.com ) 2721274Szelenkov@nginx.com 2731274Szelenkov@nginx.com time.sleep(1) 2741274Szelenkov@nginx.com 2751274Szelenkov@nginx.com sock.sendall("P/1.0\r\nHo".encode()) 2761274Szelenkov@nginx.com 2771274Szelenkov@nginx.com sock.close() 2781274Szelenkov@nginx.com 2791274Szelenkov@nginx.com def test_proxy_fragmented_body(self): 2801274Szelenkov@nginx.com _, sock = self.http( 2811274Szelenkov@nginx.com b"""GET / HTT""", raw=True, start=True, no_recv=True 2821274Szelenkov@nginx.com ) 2831274Szelenkov@nginx.com 2841274Szelenkov@nginx.com time.sleep(1) 2851274Szelenkov@nginx.com 2861274Szelenkov@nginx.com sock.sendall("P/1.0\r\nHost: localhost\r\n".encode()) 2871274Szelenkov@nginx.com sock.sendall("Content-Length: 30000\r\n".encode()) 2881274Szelenkov@nginx.com 2891274Szelenkov@nginx.com time.sleep(1) 2901274Szelenkov@nginx.com 2911274Szelenkov@nginx.com sock.sendall("\r\n".encode()) 2921274Szelenkov@nginx.com sock.sendall(("X" * 10000).encode()) 2931274Szelenkov@nginx.com 2941274Szelenkov@nginx.com time.sleep(1) 2951274Szelenkov@nginx.com 2961274Szelenkov@nginx.com sock.sendall(("X" * 10000).encode()) 2971274Szelenkov@nginx.com 2981274Szelenkov@nginx.com time.sleep(1) 2991274Szelenkov@nginx.com 3001274Szelenkov@nginx.com sock.sendall(("X" * 10000).encode()) 3011274Szelenkov@nginx.com 3021274Szelenkov@nginx.com resp = self._resp_to_dict(self.recvall(sock).decode()) 3031274Szelenkov@nginx.com sock.close() 3041274Szelenkov@nginx.com 305*1596Szelenkov@nginx.com assert resp['status'] == 200, 'status' 306*1596Szelenkov@nginx.com assert resp['body'] == "X" * 30000, 'body' 3071274Szelenkov@nginx.com 3081274Szelenkov@nginx.com def test_proxy_fragmented_body_close(self): 3091274Szelenkov@nginx.com _, sock = self.http( 3101274Szelenkov@nginx.com b"""GET / HTT""", raw=True, start=True, no_recv=True 3111274Szelenkov@nginx.com ) 3121274Szelenkov@nginx.com 3131274Szelenkov@nginx.com time.sleep(1) 3141274Szelenkov@nginx.com 3151274Szelenkov@nginx.com sock.sendall("P/1.0\r\nHost: localhost\r\n".encode()) 3161274Szelenkov@nginx.com sock.sendall("Content-Length: 30000\r\n".encode()) 3171274Szelenkov@nginx.com 3181274Szelenkov@nginx.com time.sleep(1) 3191274Szelenkov@nginx.com 3201274Szelenkov@nginx.com sock.sendall("\r\n".encode()) 3211274Szelenkov@nginx.com sock.sendall(("X" * 10000).encode()) 3221274Szelenkov@nginx.com 3231274Szelenkov@nginx.com sock.close() 3241274Szelenkov@nginx.com 3251274Szelenkov@nginx.com def test_proxy_nowhere(self): 326*1596Szelenkov@nginx.com assert 'success' in self.conf( 327*1596Szelenkov@nginx.com [{"action": {"proxy": "http://127.0.0.1:7082"}}], 'routes' 328*1596Szelenkov@nginx.com ), 'proxy path changed' 3291274Szelenkov@nginx.com 330*1596Szelenkov@nginx.com assert self.get_http10()['status'] == 502, 'status' 3311274Szelenkov@nginx.com 3321274Szelenkov@nginx.com def test_proxy_ipv6(self): 333*1596Szelenkov@nginx.com assert 'success' in self.conf( 334*1596Szelenkov@nginx.com { 335*1596Szelenkov@nginx.com "*:7080": {"pass": "routes"}, 336*1596Szelenkov@nginx.com "[::1]:7081": {'application': 'mirror'}, 337*1596Szelenkov@nginx.com }, 338*1596Szelenkov@nginx.com 'listeners', 339*1596Szelenkov@nginx.com ), 'add ipv6 listener configure' 3401274Szelenkov@nginx.com 341*1596Szelenkov@nginx.com assert 'success' in self.conf( 342*1596Szelenkov@nginx.com [{"action": {"proxy": "http://[::1]:7081"}}], 'routes' 343*1596Szelenkov@nginx.com ), 'proxy ipv6 configure' 3441274Szelenkov@nginx.com 345*1596Szelenkov@nginx.com assert self.get_http10()['status'] == 200, 'status' 3461274Szelenkov@nginx.com 3471274Szelenkov@nginx.com def test_proxy_unix(self): 348*1596Szelenkov@nginx.com addr = self.temp_dir + '/sock' 3491274Szelenkov@nginx.com 350*1596Szelenkov@nginx.com assert 'success' in self.conf( 351*1596Szelenkov@nginx.com { 352*1596Szelenkov@nginx.com "*:7080": {"pass": "routes"}, 353*1596Szelenkov@nginx.com "unix:" + addr: {'application': 'mirror'}, 354*1596Szelenkov@nginx.com }, 355*1596Szelenkov@nginx.com 'listeners', 356*1596Szelenkov@nginx.com ), 'add unix listener configure' 3571274Szelenkov@nginx.com 358*1596Szelenkov@nginx.com assert 'success' in self.conf( 359*1596Szelenkov@nginx.com [{"action": {"proxy": 'http://unix:' + addr}}], 'routes' 360*1596Szelenkov@nginx.com ), 'proxy unix configure' 3611274Szelenkov@nginx.com 362*1596Szelenkov@nginx.com assert self.get_http10()['status'] == 200, 'status' 3631274Szelenkov@nginx.com 3641274Szelenkov@nginx.com def test_proxy_delayed(self): 365*1596Szelenkov@nginx.com assert 'success' in self.conf( 366*1596Szelenkov@nginx.com {"pass": "applications/delayed"}, 'listeners/*:7081' 367*1596Szelenkov@nginx.com ), 'delayed configure' 3681274Szelenkov@nginx.com 3691274Szelenkov@nginx.com body = '0123456789' * 1000 3701274Szelenkov@nginx.com resp = self.post_http10( 3711274Szelenkov@nginx.com headers={ 3721274Szelenkov@nginx.com 'Host': 'localhost', 3731274Szelenkov@nginx.com 'Content-Type': 'text/html', 3741274Szelenkov@nginx.com 'Content-Length': str(len(body)), 3751274Szelenkov@nginx.com 'X-Parts': '2', 3761274Szelenkov@nginx.com 'X-Delay': '1', 3771274Szelenkov@nginx.com }, 3781274Szelenkov@nginx.com body=body, 3791274Szelenkov@nginx.com ) 3801274Szelenkov@nginx.com 381*1596Szelenkov@nginx.com assert resp['status'] == 200, 'status' 382*1596Szelenkov@nginx.com assert resp['body'] == body, 'body' 3831274Szelenkov@nginx.com 3841274Szelenkov@nginx.com resp = self.post_http10( 3851274Szelenkov@nginx.com headers={ 3861274Szelenkov@nginx.com 'Host': 'localhost', 3871274Szelenkov@nginx.com 'Content-Type': 'text/html', 3881274Szelenkov@nginx.com 'Content-Length': str(len(body)), 3891274Szelenkov@nginx.com 'X-Parts': '2', 3901274Szelenkov@nginx.com 'X-Delay': '1', 3911274Szelenkov@nginx.com }, 3921274Szelenkov@nginx.com body=body, 3931274Szelenkov@nginx.com ) 3941274Szelenkov@nginx.com 395*1596Szelenkov@nginx.com assert resp['status'] == 200, 'status' 396*1596Szelenkov@nginx.com assert resp['body'] == body, 'body' 3971274Szelenkov@nginx.com 3981274Szelenkov@nginx.com def test_proxy_delayed_close(self): 399*1596Szelenkov@nginx.com assert 'success' in self.conf( 400*1596Szelenkov@nginx.com {"pass": "applications/delayed"}, 'listeners/*:7081' 401*1596Szelenkov@nginx.com ), 'delayed configure' 4021274Szelenkov@nginx.com 4031274Szelenkov@nginx.com _, sock = self.post_http10( 4041274Szelenkov@nginx.com headers={ 4051274Szelenkov@nginx.com 'Host': 'localhost', 4061274Szelenkov@nginx.com 'Content-Type': 'text/html', 4071274Szelenkov@nginx.com 'Content-Length': '10000', 4081274Szelenkov@nginx.com 'X-Parts': '3', 4091274Szelenkov@nginx.com 'X-Delay': '1', 4101274Szelenkov@nginx.com }, 4111274Szelenkov@nginx.com body='0123456789' * 1000, 4121274Szelenkov@nginx.com start=True, 4131274Szelenkov@nginx.com no_recv=True, 4141274Szelenkov@nginx.com ) 4151274Szelenkov@nginx.com 416*1596Szelenkov@nginx.com assert re.search('200 OK', sock.recv(100).decode()), 'first' 4171274Szelenkov@nginx.com sock.close() 4181274Szelenkov@nginx.com 4191274Szelenkov@nginx.com _, sock = self.post_http10( 4201274Szelenkov@nginx.com headers={ 4211274Szelenkov@nginx.com 'Host': 'localhost', 4221274Szelenkov@nginx.com 'Content-Type': 'text/html', 4231274Szelenkov@nginx.com 'Content-Length': '10000', 4241274Szelenkov@nginx.com 'X-Parts': '3', 4251274Szelenkov@nginx.com 'X-Delay': '1', 4261274Szelenkov@nginx.com }, 4271274Szelenkov@nginx.com body='0123456789' * 1000, 4281274Szelenkov@nginx.com start=True, 4291274Szelenkov@nginx.com no_recv=True, 4301274Szelenkov@nginx.com ) 4311274Szelenkov@nginx.com 432*1596Szelenkov@nginx.com assert re.search('200 OK', sock.recv(100).decode()), 'second' 4331274Szelenkov@nginx.com sock.close() 4341274Szelenkov@nginx.com 435*1596Szelenkov@nginx.com @pytest.mark.skip('not yet') 4361274Szelenkov@nginx.com def test_proxy_content_length(self): 437*1596Szelenkov@nginx.com assert 'success' in self.conf( 438*1596Szelenkov@nginx.com [ 439*1596Szelenkov@nginx.com { 440*1596Szelenkov@nginx.com "action": { 441*1596Szelenkov@nginx.com "proxy": "http://127.0.0.1:" + str(self.SERVER_PORT) 4421274Szelenkov@nginx.com } 443*1596Szelenkov@nginx.com } 444*1596Szelenkov@nginx.com ], 445*1596Szelenkov@nginx.com 'routes', 446*1596Szelenkov@nginx.com ), 'proxy backend configure' 4471274Szelenkov@nginx.com 4481274Szelenkov@nginx.com resp = self.get_http10() 449*1596Szelenkov@nginx.com assert len(resp['body']) == 0, 'body lt Content-Length 0' 4501274Szelenkov@nginx.com 4511274Szelenkov@nginx.com resp = self.get_http10(headers={'Host': 'localhost', 'X-Len': '5'}) 452*1596Szelenkov@nginx.com assert len(resp['body']) == 5, 'body lt Content-Length 5' 4531274Szelenkov@nginx.com 4541274Szelenkov@nginx.com resp = self.get_http10(headers={'Host': 'localhost', 'X-Len': '9'}) 455*1596Szelenkov@nginx.com assert len(resp['body']) == 9, 'body lt Content-Length 9' 4561274Szelenkov@nginx.com 4571274Szelenkov@nginx.com resp = self.get_http10(headers={'Host': 'localhost', 'X-Len': '11'}) 458*1596Szelenkov@nginx.com assert len(resp['body']) == 10, 'body gt Content-Length 11' 4591274Szelenkov@nginx.com 4601274Szelenkov@nginx.com resp = self.get_http10(headers={'Host': 'localhost', 'X-Len': '15'}) 461*1596Szelenkov@nginx.com assert len(resp['body']) == 10, 'body gt Content-Length 15' 4621274Szelenkov@nginx.com 4631274Szelenkov@nginx.com def test_proxy_invalid(self): 4641476Szelenkov@nginx.com def check_proxy(proxy): 465*1596Szelenkov@nginx.com assert 'error' in \ 466*1596Szelenkov@nginx.com self.conf([{"action": {"proxy": proxy}}], 'routes'), \ 467*1596Szelenkov@nginx.com 'proxy invalid' 4681476Szelenkov@nginx.com 4691476Szelenkov@nginx.com check_proxy('blah') 4701476Szelenkov@nginx.com check_proxy('/blah') 4711476Szelenkov@nginx.com check_proxy('unix:/blah') 4721476Szelenkov@nginx.com check_proxy('http://blah') 4731476Szelenkov@nginx.com check_proxy('http://127.0.0.1') 4741476Szelenkov@nginx.com check_proxy('http://127.0.0.1:') 4751476Szelenkov@nginx.com check_proxy('http://127.0.0.1:blah') 4761476Szelenkov@nginx.com check_proxy('http://127.0.0.1:-1') 4771476Szelenkov@nginx.com check_proxy('http://127.0.0.1:7080b') 4781476Szelenkov@nginx.com check_proxy('http://[]') 4791476Szelenkov@nginx.com check_proxy('http://[]:7080') 4801476Szelenkov@nginx.com check_proxy('http://[:]:7080') 4811476Szelenkov@nginx.com check_proxy('http://[::7080') 4821274Szelenkov@nginx.com 4831274Szelenkov@nginx.com def test_proxy_loop(self): 484*1596Szelenkov@nginx.com skip_alert( 485*1596Szelenkov@nginx.com r'socket.*failed', 486*1596Szelenkov@nginx.com r'accept.*failed', 487*1596Szelenkov@nginx.com r'new connections are not accepted', 4881465Szelenkov@nginx.com ) 4891274Szelenkov@nginx.com self.conf( 4901274Szelenkov@nginx.com { 4911274Szelenkov@nginx.com "listeners": { 4921274Szelenkov@nginx.com "*:7080": {"pass": "routes"}, 4931274Szelenkov@nginx.com "*:7081": {"pass": "applications/mirror"}, 4941274Szelenkov@nginx.com "*:7082": {"pass": "routes"}, 4951274Szelenkov@nginx.com }, 4961274Szelenkov@nginx.com "routes": [{"action": {"proxy": "http://127.0.0.1:7082"}}], 4971274Szelenkov@nginx.com "applications": { 4981274Szelenkov@nginx.com "mirror": { 4991274Szelenkov@nginx.com "type": "python", 5001274Szelenkov@nginx.com "processes": {"spare": 0}, 501*1596Szelenkov@nginx.com "path": option.test_dir + "/python/mirror", 502*1596Szelenkov@nginx.com "working_directory": option.test_dir + "/python/mirror", 5031274Szelenkov@nginx.com "module": "wsgi", 5041274Szelenkov@nginx.com }, 5051274Szelenkov@nginx.com }, 5061274Szelenkov@nginx.com } 5071274Szelenkov@nginx.com ) 5081274Szelenkov@nginx.com 5091274Szelenkov@nginx.com self.get_http10(no_recv=True) 5101465Szelenkov@nginx.com self.get_http10(read_timeout=1) 511