Repository URL to install this package:
|
Version:
1.26.9 ▾
|
from test import SHORT_TIMEOUT
from test.with_dummyserver import test_connectionpool
import pytest
import dummyserver.testcase
import urllib3.exceptions
import urllib3.util.retry
import urllib3.util.url
from urllib3.contrib import appengine
# This class is used so we can re-use the tests from the connection pool.
# It proxies all requests to the manager.
class MockPool(object):
def __init__(self, host, port, manager, scheme="http"):
self.host = host
self.port = port
self.manager = manager
self.scheme = scheme
def request(self, method, url, *args, **kwargs):
url = self._absolute_url(url)
return self.manager.request(method, url, *args, **kwargs)
def urlopen(self, method, url, *args, **kwargs):
url = self._absolute_url(url)
return self.manager.urlopen(method, url, *args, **kwargs)
def _absolute_url(self, path):
return urllib3.util.url.Url(
scheme=self.scheme, host=self.host, port=self.port, path=path
).url
# Note that this doesn't run in the sandbox, it only runs with the URLFetch
# API stub enabled. There's no need to enable the sandbox as we know for a fact
# that URLFetch is used by the connection manager.
@pytest.mark.usefixtures("testbed")
class TestGAEConnectionManager(test_connectionpool.TestConnectionPool):
def setup_method(self, method):
self.manager = appengine.AppEngineManager()
self.pool = MockPool(self.host, self.port, self.manager)
# Tests specific to AppEngineManager
def test_exceptions(self):
# DeadlineExceededError -> TimeoutError
with pytest.raises(urllib3.exceptions.TimeoutError):
self.pool.request(
"GET",
"/sleep?seconds={}".format(5 * SHORT_TIMEOUT),
timeout=SHORT_TIMEOUT,
)
# InvalidURLError -> ProtocolError
with pytest.raises(urllib3.exceptions.ProtocolError):
self.manager.request("GET", "ftp://invalid/url")
# DownloadError -> ProtocolError
with pytest.raises(urllib3.exceptions.ProtocolError):
self.manager.request("GET", "http://0.0.0.0")
# ResponseTooLargeError -> AppEnginePlatformError
with pytest.raises(appengine.AppEnginePlatformError):
self.pool.request(
"GET", "/nbytes?length=33554433"
) # One byte over 32 megabytes.
# URLFetch reports the request too large error as a InvalidURLError,
# which maps to a AppEnginePlatformError.
body = b"1" * 10485761 # One byte over 10 megabytes.
with pytest.raises(appengine.AppEnginePlatformError):
self.manager.request("POST", "/", body=body)
# Re-used tests below this line.
# Subsumed tests
test_timeout_float = None # Covered by test_exceptions.
# Non-applicable tests
test_conn_closed = None
test_nagle = None
test_socket_options = None
test_disable_default_socket_options = None
test_defaults_are_applied = None
test_tunnel = None
test_keepalive = None
test_keepalive_close = None
test_connection_count = None
test_connection_count_bigpool = None
test_for_double_release = None
test_release_conn_parameter = None
test_stream_keepalive = None
test_cleanup_on_connection_error = None
test_read_chunked_short_circuit = None
test_read_chunked_on_closed_response = None
# Tests that should likely be modified for appengine specific stuff
test_timeout = None
test_connect_timeout = None
test_connection_error_retries = None
test_total_timeout = None
test_none_total_applies_connect = None
test_timeout_success = None
test_source_address_error = None
test_bad_connect = None
test_partial_response = None
test_dns_error = None
@pytest.mark.usefixtures("testbed")
class TestGAEConnectionManagerWithSSL(dummyserver.testcase.HTTPSDummyServerTestCase):
def setup_method(self, method):
self.manager = appengine.AppEngineManager()
self.pool = MockPool(self.host, self.port, self.manager, "https")
def test_exceptions(self):
# SSLCertificateError -> SSLError
# SSLError is raised with dummyserver because URLFetch doesn't allow
# self-signed certs.
with pytest.raises(urllib3.exceptions.SSLError):
self.pool.request("GET", "/")
@pytest.mark.usefixtures("testbed")
class TestGAERetry(test_connectionpool.TestRetry):
def setup_method(self, method):
self.manager = appengine.AppEngineManager()
self.pool = MockPool(self.host, self.port, self.manager)
def test_default_method_whitelist_retried(self):
"""urllib3 should retry methods in the default method whitelist"""
retry = urllib3.util.retry.Retry(total=1, status_forcelist=[418])
# Use HEAD instead of OPTIONS, as URLFetch doesn't support OPTIONS
resp = self.pool.request(
"HEAD",
"/successful_retry",
headers={"test-name": "test_default_whitelist"},
retries=retry,
)
assert resp.status == 200
def test_retry_return_in_response(self):
headers = {"test-name": "test_retry_return_in_response"}
retry = urllib3.util.retry.Retry(total=2, status_forcelist=[418])
resp = self.pool.request(
"GET", "/successful_retry", headers=headers, retries=retry
)
assert resp.status == 200
assert resp.retries.total == 1
# URLFetch use absolute urls.
assert resp.retries.history == (
urllib3.util.retry.RequestHistory(
"GET", self.pool._absolute_url("/successful_retry"), None, 418, None
),
)
# test_max_retry = None
# test_disabled_retry = None
# We don't need these tests because URLFetch resolves its own redirects.
test_retry_redirect_history = None
test_multi_redirect_history = None
@pytest.mark.usefixtures("testbed")
class TestGAERetryAfter(test_connectionpool.TestRetryAfter):
def setup_method(self, method):
# Disable urlfetch which doesn't respect Retry-After header.
self.manager = appengine.AppEngineManager(urlfetch_retries=False)
self.pool = MockPool(self.host, self.port, self.manager)
def test_gae_environ():
assert not appengine.is_appengine()
assert not appengine.is_appengine_sandbox()
assert not appengine.is_local_appengine()
assert not appengine.is_prod_appengine()
assert not appengine.is_prod_appengine_mvms()