Stop leaking quite so many connections
While investigating the failures when you move func tests to py3, I noticed a whole bunch of ResourceWarning: unclosed <socket.socket ...> noise. This should fix it. While we're at it, make get_capabilities less stupid. Change-Id: I3913e9334090b04a78143e0b70f621aad30fc642 Related-Change: I86d24104033b490a35178fc504d88c1e4a566628
This commit is contained in:
parent
9acdfe0b46
commit
411ef48e5b
@ -402,6 +402,7 @@ class HTTPConnection(object):
|
|||||||
self.request_session = requests.Session()
|
self.request_session = requests.Session()
|
||||||
# Don't use requests's default headers
|
# Don't use requests's default headers
|
||||||
self.request_session.headers = None
|
self.request_session.headers = None
|
||||||
|
self.resp = None
|
||||||
if self.parsed_url.scheme not in ('http', 'https'):
|
if self.parsed_url.scheme not in ('http', 'https'):
|
||||||
raise ClientException('Unsupported scheme "%s" in url "%s"'
|
raise ClientException('Unsupported scheme "%s" in url "%s"'
|
||||||
% (self.parsed_url.scheme, url))
|
% (self.parsed_url.scheme, url))
|
||||||
@ -506,6 +507,11 @@ class HTTPConnection(object):
|
|||||||
|
|
||||||
return self.resp
|
return self.resp
|
||||||
|
|
||||||
|
def close(self):
|
||||||
|
if self.resp:
|
||||||
|
self.resp.close()
|
||||||
|
self.request_session.close()
|
||||||
|
|
||||||
|
|
||||||
def http_connection(*arg, **kwarg):
|
def http_connection(*arg, **kwarg):
|
||||||
""":returns: tuple of (parsed url, connection object)"""
|
""":returns: tuple of (parsed url, connection object)"""
|
||||||
@ -527,6 +533,8 @@ def get_auth_1_0(url, user, key, snet, **kwargs):
|
|||||||
conn.request(method, parsed.path, '', headers)
|
conn.request(method, parsed.path, '', headers)
|
||||||
resp = conn.getresponse()
|
resp = conn.getresponse()
|
||||||
body = resp.read()
|
body = resp.read()
|
||||||
|
resp.close()
|
||||||
|
conn.close()
|
||||||
http_log((url, method,), headers, resp, body)
|
http_log((url, method,), headers, resp, body)
|
||||||
url = resp.getheader('x-storage-url')
|
url = resp.getheader('x-storage-url')
|
||||||
|
|
||||||
@ -1651,11 +1659,8 @@ class Connection(object):
|
|||||||
if (self.http_conn and isinstance(self.http_conn, tuple)
|
if (self.http_conn and isinstance(self.http_conn, tuple)
|
||||||
and len(self.http_conn) > 1):
|
and len(self.http_conn) > 1):
|
||||||
conn = self.http_conn[1]
|
conn = self.http_conn[1]
|
||||||
if hasattr(conn, 'close') and callable(conn.close):
|
conn.close()
|
||||||
# XXX: Our HTTPConnection object has no close, should be
|
self.http_conn = None
|
||||||
# trying to close the requests.Session here?
|
|
||||||
conn.close()
|
|
||||||
self.http_conn = None
|
|
||||||
|
|
||||||
def get_auth(self):
|
def get_auth(self):
|
||||||
self.url, self.token = get_auth(self.authurl, self.user, self.key,
|
self.url, self.token = get_auth(self.authurl, self.user, self.key,
|
||||||
@ -1715,10 +1720,10 @@ class Connection(object):
|
|||||||
try:
|
try:
|
||||||
if not self.url or not self.token:
|
if not self.url or not self.token:
|
||||||
self.url, self.token = self.get_auth()
|
self.url, self.token = self.get_auth()
|
||||||
self.http_conn = None
|
self.close()
|
||||||
if self.service_auth and not self.service_token:
|
if self.service_auth and not self.service_token:
|
||||||
self.url, self.service_token = self.get_service_auth()
|
self.url, self.service_token = self.get_service_auth()
|
||||||
self.http_conn = None
|
self.close()
|
||||||
self.auth_end_time = time()
|
self.auth_end_time = time()
|
||||||
if not self.http_conn:
|
if not self.http_conn:
|
||||||
self.http_conn = self.http_connection()
|
self.http_conn = self.http_connection()
|
||||||
@ -1908,8 +1913,7 @@ class Connection(object):
|
|||||||
url = url or self.url
|
url = url or self.url
|
||||||
if not url:
|
if not url:
|
||||||
url, _ = self.get_auth()
|
url, _ = self.get_auth()
|
||||||
scheme = urlparse(url).scheme
|
parsed = urlparse(urljoin(url, '/info'))
|
||||||
netloc = urlparse(url).netloc
|
if not self.http_conn:
|
||||||
url = scheme + '://' + netloc + '/info'
|
self.http_conn = self.http_connection(url)
|
||||||
http_conn = self.http_connection(url)
|
return get_capabilities((parsed, self.http_conn[1]))
|
||||||
return get_capabilities(http_conn)
|
|
||||||
|
@ -108,6 +108,7 @@ class TestFunctional(unittest.TestCase):
|
|||||||
self.conn.delete_container(container)
|
self.conn.delete_container(container)
|
||||||
except swiftclient.ClientException:
|
except swiftclient.ClientException:
|
||||||
pass
|
pass
|
||||||
|
self.conn.close()
|
||||||
|
|
||||||
def _check_account_headers(self, headers):
|
def _check_account_headers(self, headers):
|
||||||
headers_to_check = [
|
headers_to_check = [
|
||||||
|
@ -2532,6 +2532,9 @@ class TestConnection(MockHttpTest):
|
|||||||
def read(self, *args, **kwargs):
|
def read(self, *args, **kwargs):
|
||||||
return ''
|
return ''
|
||||||
|
|
||||||
|
def close(self):
|
||||||
|
pass
|
||||||
|
|
||||||
def local_http_connection(url, proxy=None, cacert=None,
|
def local_http_connection(url, proxy=None, cacert=None,
|
||||||
insecure=False, cert=None, cert_key=None,
|
insecure=False, cert=None, cert_key=None,
|
||||||
ssl_compression=True, timeout=None):
|
ssl_compression=True, timeout=None):
|
||||||
@ -2901,6 +2904,9 @@ class TestCloseConnection(MockHttpTest):
|
|||||||
self.assertIsNone(conn.http_conn)
|
self.assertIsNone(conn.http_conn)
|
||||||
conn.close()
|
conn.close()
|
||||||
self.assertIsNone(conn.http_conn)
|
self.assertIsNone(conn.http_conn)
|
||||||
|
# Can re-close
|
||||||
|
conn.close()
|
||||||
|
self.assertIsNone(conn.http_conn)
|
||||||
|
|
||||||
def test_close_ok(self):
|
def test_close_ok(self):
|
||||||
url = 'http://www.test.com'
|
url = 'http://www.test.com'
|
||||||
@ -2911,7 +2917,7 @@ class TestCloseConnection(MockHttpTest):
|
|||||||
self.assertEqual(len(conn.http_conn), 2)
|
self.assertEqual(len(conn.http_conn), 2)
|
||||||
http_conn_obj = conn.http_conn[1]
|
http_conn_obj = conn.http_conn[1]
|
||||||
self.assertIsInstance(http_conn_obj, c.HTTPConnection)
|
self.assertIsInstance(http_conn_obj, c.HTTPConnection)
|
||||||
self.assertFalse(hasattr(http_conn_obj, 'close'))
|
self.assertTrue(hasattr(http_conn_obj, 'close'))
|
||||||
conn.close()
|
conn.close()
|
||||||
|
|
||||||
|
|
||||||
|
@ -78,6 +78,10 @@ class StubResponse(object):
|
|||||||
self.body = body
|
self.body = body
|
||||||
self.headers = headers or {}
|
self.headers = headers or {}
|
||||||
|
|
||||||
|
def __repr__(self):
|
||||||
|
return '%s(%r, %r, %r)' % (self.__class__.__name__, self.status,
|
||||||
|
self.body, self.headers)
|
||||||
|
|
||||||
|
|
||||||
def fake_http_connect(*code_iter, **kwargs):
|
def fake_http_connect(*code_iter, **kwargs):
|
||||||
"""
|
"""
|
||||||
@ -102,7 +106,6 @@ def fake_http_connect(*code_iter, **kwargs):
|
|||||||
self.etag = etag
|
self.etag = etag
|
||||||
self.content = self.body = body
|
self.content = self.body = body
|
||||||
self.timestamp = timestamp
|
self.timestamp = timestamp
|
||||||
self._is_closed = True
|
|
||||||
self.headers = headers or {}
|
self.headers = headers or {}
|
||||||
self.request = None
|
self.request = None
|
||||||
|
|
||||||
@ -162,6 +165,9 @@ def fake_http_connect(*code_iter, **kwargs):
|
|||||||
def getheader(self, name, default=None):
|
def getheader(self, name, default=None):
|
||||||
return dict(self.getheaders()).get(name.lower(), default)
|
return dict(self.getheaders()).get(name.lower(), default)
|
||||||
|
|
||||||
|
def close(self):
|
||||||
|
pass
|
||||||
|
|
||||||
timestamps_iter = iter(kwargs.get('timestamps') or ['1'] * len(code_iter))
|
timestamps_iter = iter(kwargs.get('timestamps') or ['1'] * len(code_iter))
|
||||||
etag_iter = iter(kwargs.get('etags') or [None] * len(code_iter))
|
etag_iter = iter(kwargs.get('etags') or [None] * len(code_iter))
|
||||||
x = kwargs.get('missing_container', [False] * len(code_iter))
|
x = kwargs.get('missing_container', [False] * len(code_iter))
|
||||||
@ -228,7 +234,8 @@ class MockHttpTest(unittest.TestCase):
|
|||||||
parsed, _conn = _orig_http_connection(url, proxy=proxy)
|
parsed, _conn = _orig_http_connection(url, proxy=proxy)
|
||||||
|
|
||||||
class RequestsWrapper(object):
|
class RequestsWrapper(object):
|
||||||
pass
|
def close(self):
|
||||||
|
pass
|
||||||
conn = RequestsWrapper()
|
conn = RequestsWrapper()
|
||||||
|
|
||||||
def request(method, path, *args, **kwargs):
|
def request(method, path, *args, **kwargs):
|
||||||
|
Loading…
Reference in New Issue
Block a user