| import socket | |
| import time | |
| import pytest | |
| from .env import H2Conf | |
| from pyhttpd.curl import CurlPiper | |
| class TestTimeout: | |
| # Check that base servers 'Timeout' setting is observed on SSL handshake | |
| def test_h2_105_01(self, env): | |
| conf = H2Conf(env) | |
| conf.add(""" | |
| AcceptFilter http none | |
| Timeout 1.5 | |
| """) | |
| conf.add_vhost_cgi() | |
| conf.install() | |
| assert env.apache_restart() == 0 | |
| host = 'localhost' | |
| # read with a longer timeout than the server | |
| sock = socket.create_connection((host, int(env.https_port))) | |
| try: | |
| # on some OS, the server does not see our connection until there is | |
| # something incoming | |
| sock.send(b'0') | |
| sock.settimeout(4) | |
| buff = sock.recv(1024) | |
| assert buff == b'' | |
| except Exception as ex: | |
| print(f"server did not close in time: {ex}") | |
| assert False | |
| sock.close() | |
| # read with a shorter timeout than the server | |
| sock = socket.create_connection((host, int(env.https_port))) | |
| try: | |
| sock.settimeout(0.5) | |
| sock.recv(1024) | |
| assert False | |
| except Exception as ex: | |
| print(f"as expected: {ex}") | |
| sock.close() | |
| # | |
| time.sleep(1) # let the log flush | |
| env.httpd_error_log.ignore_recent( | |
| lognos = [ | |
| "AH10373" # SSL handshake was not completed | |
| ] | |
| ) | |
| # Check that mod_reqtimeout handshake setting takes effect | |
| def test_h2_105_02(self, env): | |
| conf = H2Conf(env) | |
| conf.add(""" | |
| AcceptFilter http none | |
| Timeout 10 | |
| RequestReadTimeout handshake=1 header=5 body=10 | |
| """) | |
| conf.add_vhost_cgi() | |
| conf.install() | |
| assert env.apache_restart() == 0 | |
| host = 'localhost' | |
| # read with a longer timeout than the server | |
| sock = socket.create_connection((host, int(env.https_port))) | |
| try: | |
| # on some OS, the server does not see our connection until there is | |
| # something incoming | |
| sock.send(b'0') | |
| sock.settimeout(4) | |
| buff = sock.recv(1024) | |
| assert buff == b'' | |
| except Exception as ex: | |
| print(f"server did not close in time: {ex}") | |
| assert False | |
| sock.close() | |
| # read with a shorter timeout than the server | |
| sock = socket.create_connection((host, int(env.https_port))) | |
| try: | |
| sock.settimeout(0.5) | |
| sock.recv(1024) | |
| assert False | |
| except Exception as ex: | |
| print(f"as expected: {ex}") | |
| sock.close() | |
| # | |
| time.sleep(1) # let the log flush | |
| env.httpd_error_log.ignore_recent( | |
| lognos = [ | |
| "AH10373" # SSL handshake was not completed | |
| ] | |
| ) | |
| # Check that mod_reqtimeout handshake setting do no longer apply to handshaked | |
| # connections. See <https://github.com/icing/mod_h2/issues/196>. | |
| def test_h2_105_03(self, env): | |
| conf = H2Conf(env) | |
| conf.add(""" | |
| Timeout 10 | |
| RequestReadTimeout handshake=1 header=5 body=10 | |
| """) | |
| conf.add_vhost_cgi() | |
| conf.install() | |
| assert env.apache_restart() == 0 | |
| url = env.mkurl("https", "cgi", "/necho.py") | |
| r = env.curl_get(url, 5, options=[ | |
| "-vvv", | |
| "-F", ("count=%d" % 100), | |
| "-F", ("text=%s" % "abcdefghijklmnopqrstuvwxyz"), | |
| "-F", ("wait1=%f" % 1.5), | |
| ]) | |
| assert r.response["status"] == 200 | |
| def test_h2_105_10(self, env): | |
| # just a check without delays if all is fine | |
| conf = H2Conf(env) | |
| conf.add_vhost_cgi() | |
| conf.install() | |
| assert env.apache_restart() == 0 | |
| url = env.mkurl("https", "cgi", "/h2test/delay") | |
| piper = CurlPiper(env=env, url=url) | |
| piper.start() | |
| stdout, stderr = piper.close() | |
| assert piper.exitcode == 0 | |
| assert len("".join(stdout)) == 3 * 8192 | |
| def test_h2_105_11(self, env): | |
| # short connection timeout, longer stream delay | |
| # connection timeout must not abort ongoing streams | |
| conf = H2Conf(env) | |
| conf.add_vhost_cgi() | |
| conf.add("Timeout 1") | |
| conf.install() | |
| assert env.apache_restart() == 0 | |
| url = env.mkurl("https", "cgi", "/h2test/delay?1200ms") | |
| piper = CurlPiper(env=env, url=url) | |
| piper.start() | |
| stdout, stderr = piper.close() | |
| assert len("".join(stdout)) == 3 * 8192 | |
| def test_h2_105_12(self, env): | |
| # long connection timeout, short stream timeout | |
| # sending a slow POST | |
| env.require(env.curl_is_at_least('8.0.0'), | |
| 'need at least curl v8.0.0 for this', | |
| dep='curl >= 8.0.0', | |
| detected=f"curl {env.curl_version_str()}") | |
| if not env.httpd_is_at_least("2.5.0"): | |
| pytest.skip(f'need at least httpd 2.5.0 for this') | |
| conf = H2Conf(env) | |
| conf.add_vhost_cgi() | |
| conf.add("Timeout 10") | |
| conf.add("H2StreamTimeout 1") | |
| conf.install() | |
| assert env.apache_restart() == 0 | |
| url = env.mkurl("https", "cgi", "/h2test/delay?5") | |
| piper = CurlPiper(env=env, url=url) | |
| piper.start() | |
| for _ in range(3): | |
| time.sleep(2) | |
| try: | |
| piper.send("0123456789\n") | |
| except (BrokenPipeError, OSError): | |
| break | |
| piper.close() | |
| assert piper.response, f'{piper}' | |
| assert piper.response['status'] == 408, f"{piper.response}" |