##// END OF EJS Templates
tests: fixed stream test chunking that returned wrongly str not bytes
super-admin -
r5168:7fe32e44 default
parent child Browse files
Show More
@@ -1,136 +1,139 b''
1 1
2 2
3 3 # Copyright (C) 2016-2023 RhodeCode GmbH
4 4 #
5 5 # This program is free software: you can redistribute it and/or modify
6 6 # it under the terms of the GNU Affero General Public License, version 3
7 7 # (only), as published by the Free Software Foundation.
8 8 #
9 9 # This program is distributed in the hope that it will be useful,
10 10 # but WITHOUT ANY WARRANTY; without even the implied warranty of
11 11 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 12 # GNU General Public License for more details.
13 13 #
14 14 # You should have received a copy of the GNU Affero General Public License
15 15 # along with this program. If not, see <http://www.gnu.org/licenses/>.
16 16 #
17 17 # This program is dual-licensed. If you wish to learn more about the
18 18 # RhodeCode Enterprise Edition, including its added features, Support services,
19 19 # and proprietary license terms, please see https://rhodecode.com/licenses/
20 20
21 21 """
22 22 Checking the chunked data transfer via HTTP
23 23 """
24 24
25 25 import os
26 26 import time
27 27 import subprocess
28 28
29 29 import pytest
30 30 import requests
31 31
32 32 from rhodecode.lib.middleware.utils import scm_app_http
33 33 from rhodecode.tests.utils import wait_for_url
34 34
35 35
36 36 def test_does_chunked_end_to_end_transfer(scm_app):
37 37 response = requests.post(scm_app, data='', stream=True)
38 38 assert response.headers['Transfer-Encoding'] == 'chunked'
39 39 times = [time.time() for chunk in response.raw.read_chunked()]
40 40 assert times[1] - times[0] > 0.1, "Chunks arrived at the same time"
41 41
42 42
43 SCM_APP_URL_TMPL = 'http://0.0.0.0:{port}'
44
45
43 46 @pytest.fixture()
44 47 def echo_app_chunking(request, available_port_factory):
45 48 """
46 49 Run the EchoApp via Waitress in a subprocess.
47 50
48 51 Return the URL endpoint to reach the app.
49 52 """
50 53 port = available_port_factory()
51 54 command = (
52 55 'waitress-serve --send-bytes 1 --port {port} --call '
53 56 'rhodecode.tests.lib.middleware.utils.test_scm_app_http_chunking'
54 57 ':create_echo_app')
55 58 command = command.format(port=port)
56 59 proc = subprocess.Popen(command.split(' '), bufsize=0)
57 echo_app_url = 'http://localhost:' + str(port)
60 echo_app_url = SCM_APP_URL_TMPL.format(port=port)
58 61
59 62 @request.addfinalizer
60 63 def stop_echo_app():
61 64 proc.kill()
62 65
63 66 return echo_app_url
64 67
65 68
66 69 @pytest.fixture()
67 70 def scm_app(request, available_port_factory, echo_app_chunking):
68 71 """
69 72 Run the scm_app in Waitress.
70 73
71 74 Returns the URL endpoint where this app can be reached.
72 75 """
73 76 port = available_port_factory()
74 77 command = (
75 78 'waitress-serve --send-bytes 1 --port {port} --call '
76 79 'rhodecode.tests.lib.middleware.utils.test_scm_app_http_chunking'
77 80 ':create_scm_app')
78 81 command = command.format(port=port)
79 82 env = os.environ.copy()
80 83 env["RC_ECHO_URL"] = echo_app_chunking
81 84 proc = subprocess.Popen(command.split(' '), bufsize=0, env=env)
82 scm_app_url = 'http://localhost:' + str(port)
85 scm_app_url = SCM_APP_URL_TMPL.format(port=port)
83 86 wait_for_url(scm_app_url)
84 87
85 88 @request.addfinalizer
86 89 def stop_echo_app():
87 90 proc.kill()
88 91
89 92 return scm_app_url
90 93
91 94
92 95 class EchoApp(object):
93 96 """
94 97 Stub WSGI application which returns a chunked response to every request.
95 98 """
96 99
97 100 def __init__(self, repo_path, repo_name, config):
98 101 self._repo_path = repo_path
99 102
100 103 def __call__(self, environ, start_response):
101 104 environ['wsgi.input'].read()
102 105 status = '200 OK'
103 106 headers = []
104 107 start_response(status, headers)
105 108 return result_generator()
106 109
107 110
108 111 def result_generator():
109 112 """
110 113 Simulate chunked results.
111 114
112 115 The intended usage is to simulate a chunked response as we would get it
113 116 out of a vcs operation during a call to "hg clone".
114 117 """
115 yield 'waiting 2 seconds'
118 yield b'waiting 2 seconds'
116 119 # Wait long enough so that the first chunk can go out
117 120 time.sleep(2)
118 yield 'final chunk'
121 yield b'final chunk'
119 122 # Another small wait, otherwise they go together
120 123 time.sleep(0.1)
121 124
122 125
123 126 def create_echo_app():
124 127 """
125 128 Create EchoApp filled with stub data.
126 129 """
127 130 return EchoApp('stub_path', 'repo_name', {})
128 131
129 132
130 133 def create_scm_app():
131 134 """
132 135 Create a scm_app hooked up to speak to EchoApp.
133 136 """
134 137 echo_app_url = os.environ["RC_ECHO_URL"]
135 138 return scm_app_http.VcsHttpProxy(
136 139 echo_app_url, 'stub_path', 'stub_name', None)
General Comments 0
You need to be logged in to leave comments. Login now