Body of http responses included in Swift error msg

The body of http responses is included in error messages from
swift.common.client and bin/swift if the body exists

Includes changes requested by Juan Martinez

Includes changes requested by David Goetz

Fixed pep8 warnings

Bug 949843

Change-Id: Ib998280762b084dd46f8c0f4524eed20513de82b
This commit is contained in:
Eamonn O'Toole 2012-03-08 15:38:49 +00:00
parent 9e713e1078
commit 43ad1edd5d
3 changed files with 118 additions and 60 deletions

View File

@ -80,7 +80,7 @@ class ClientException(Exception):
def __init__(self, msg, http_scheme='', http_host='', http_port='',
http_path='', http_query='', http_status=0, http_reason='',
http_device=''):
http_device='', http_response_content=''):
Exception.__init__(self, msg)
self.msg = msg
self.http_scheme = http_scheme
@ -91,6 +91,7 @@ class ClientException(Exception):
self.http_status = http_status
self.http_reason = http_reason
self.http_device = http_device
self.http_response_content = http_response_content
def __str__(self):
a = self.msg
@ -120,6 +121,12 @@ class ClientException(Exception):
b = '%s: device %s' % (b, self.http_device)
else:
b = 'device %s' % self.http_device
if self.http_response_content:
if len(self.http_response_content) <= 60:
b += ' %s' % self.http_response_content
else:
b += ' [first 60 chars of response] %s' % \
self.http_response_content[:60]
return b and '%s: %s' % (a, b) or a
@ -306,11 +313,11 @@ def get_account(url, token, marker=None, limit=None, prefix=None,
for header, value in resp.getheaders():
resp_headers[header.lower()] = value
if resp.status < 200 or resp.status >= 300:
resp.read()
body = resp.read()
raise ClientException('Account GET failed', http_scheme=parsed.scheme,
http_host=conn.host, http_port=conn.port,
http_path=parsed.path, http_query=qs, http_status=resp.status,
http_reason=resp.reason)
http_reason=resp.reason, http_response_content=body)
if resp.status == 204:
resp.read()
return resp_headers, []
@ -335,12 +342,12 @@ def head_account(url, token, http_conn=None):
parsed, conn = http_connection(url)
conn.request('HEAD', parsed.path, '', {'X-Auth-Token': token})
resp = conn.getresponse()
resp.read()
body = resp.read()
if resp.status < 200 or resp.status >= 300:
raise ClientException('Account HEAD failed', http_scheme=parsed.scheme,
http_host=conn.host, http_port=conn.port,
http_path=parsed.path, http_status=resp.status,
http_reason=resp.reason)
http_reason=resp.reason, http_response_content=body)
resp_headers = {}
for header, value in resp.getheaders():
resp_headers[header.lower()] = value
@ -365,7 +372,7 @@ def post_account(url, token, headers, http_conn=None):
headers['X-Auth-Token'] = token
conn.request('POST', parsed.path, '', headers)
resp = conn.getresponse()
resp.read()
body = resp.read()
if resp.status < 200 or resp.status >= 300:
raise ClientException('Account POST failed',
http_scheme=parsed.scheme,
@ -373,7 +380,8 @@ def post_account(url, token, headers, http_conn=None):
http_port=conn.port,
http_path=parsed.path,
http_status=resp.status,
http_reason=resp.reason)
http_reason=resp.reason,
http_response_content=body)
def get_container(url, token, container, marker=None, limit=None,
@ -427,11 +435,12 @@ def get_container(url, token, container, marker=None, limit=None,
conn.request('GET', '%s?%s' % (path, qs), '', {'X-Auth-Token': token})
resp = conn.getresponse()
if resp.status < 200 or resp.status >= 300:
resp.read()
body = resp.read()
raise ClientException('Container GET failed',
http_scheme=parsed.scheme, http_host=conn.host,
http_port=conn.port, http_path=path, http_query=qs,
http_status=resp.status, http_reason=resp.reason)
http_status=resp.status, http_reason=resp.reason,
http_response_content=body)
resp_headers = {}
for header, value in resp.getheaders():
resp_headers[header.lower()] = value
@ -461,12 +470,12 @@ def head_container(url, token, container, http_conn=None):
path = '%s/%s' % (parsed.path, quote(container))
conn.request('HEAD', path, '', {'X-Auth-Token': token})
resp = conn.getresponse()
resp.read()
body = resp.read()
if resp.status < 200 or resp.status >= 300:
raise ClientException('Container HEAD failed',
http_scheme=parsed.scheme, http_host=conn.host,
http_port=conn.port, http_path=path, http_status=resp.status,
http_reason=resp.reason)
http_reason=resp.reason, http_response_content=body)
resp_headers = {}
for header, value in resp.getheaders():
resp_headers[header.lower()] = value
@ -495,12 +504,12 @@ def put_container(url, token, container, headers=None, http_conn=None):
headers['X-Auth-Token'] = token
conn.request('PUT', path, '', headers)
resp = conn.getresponse()
resp.read()
body = resp.read()
if resp.status < 200 or resp.status >= 300:
raise ClientException('Container PUT failed',
http_scheme=parsed.scheme, http_host=conn.host,
http_port=conn.port, http_path=path, http_status=resp.status,
http_reason=resp.reason)
http_reason=resp.reason, http_response_content=body)
def post_container(url, token, container, headers, http_conn=None):
@ -523,12 +532,12 @@ def post_container(url, token, container, headers, http_conn=None):
headers['X-Auth-Token'] = token
conn.request('POST', path, '', headers)
resp = conn.getresponse()
resp.read()
body = resp.read()
if resp.status < 200 or resp.status >= 300:
raise ClientException('Container POST failed',
http_scheme=parsed.scheme, http_host=conn.host,
http_port=conn.port, http_path=path, http_status=resp.status,
http_reason=resp.reason)
http_reason=resp.reason, http_response_content=body)
def delete_container(url, token, container, http_conn=None):
@ -549,12 +558,12 @@ def delete_container(url, token, container, http_conn=None):
path = '%s/%s' % (parsed.path, quote(container))
conn.request('DELETE', path, '', {'X-Auth-Token': token})
resp = conn.getresponse()
resp.read()
body = resp.read()
if resp.status < 200 or resp.status >= 300:
raise ClientException('Container DELETE failed',
http_scheme=parsed.scheme, http_host=conn.host,
http_port=conn.port, http_path=path, http_status=resp.status,
http_reason=resp.reason)
http_reason=resp.reason, http_response_content=body)
def get_object(url, token, container, name, http_conn=None,
@ -584,10 +593,11 @@ def get_object(url, token, container, name, http_conn=None,
conn.request('GET', path, '', {'X-Auth-Token': token})
resp = conn.getresponse()
if resp.status < 200 or resp.status >= 300:
resp.read()
body = resp.read()
raise ClientException('Object GET failed', http_scheme=parsed.scheme,
http_host=conn.host, http_port=conn.port, http_path=path,
http_status=resp.status, http_reason=resp.reason)
http_status=resp.status, http_reason=resp.reason,
http_response_content=body)
if resp_chunk_size:
def _object_body():
@ -625,11 +635,12 @@ def head_object(url, token, container, name, http_conn=None):
path = '%s/%s/%s' % (parsed.path, quote(container), quote(name))
conn.request('HEAD', path, '', {'X-Auth-Token': token})
resp = conn.getresponse()
resp.read()
body = resp.read()
if resp.status < 200 or resp.status >= 300:
raise ClientException('Object HEAD failed', http_scheme=parsed.scheme,
http_host=conn.host, http_port=conn.port, http_path=path,
http_status=resp.status, http_reason=resp.reason)
http_status=resp.status, http_reason=resp.reason,
http_response_content=body)
resp_headers = {}
for header, value in resp.getheaders():
resp_headers[header.lower()] = value
@ -719,11 +730,12 @@ def put_object(url, token=None, container=None, name=None, contents=None,
else:
conn.request('PUT', path, contents, headers)
resp = conn.getresponse()
resp.read()
body = resp.read()
if resp.status < 200 or resp.status >= 300:
raise ClientException('Object PUT failed', http_scheme=parsed.scheme,
http_host=conn.host, http_port=conn.port, http_path=path,
http_status=resp.status, http_reason=resp.reason)
http_status=resp.status, http_reason=resp.reason,
http_response_content=body)
return resp.getheader('etag', '').strip('"')
@ -748,11 +760,12 @@ def post_object(url, token, container, name, headers, http_conn=None):
headers['X-Auth-Token'] = token
conn.request('POST', path, '', headers)
resp = conn.getresponse()
resp.read()
body = resp.read()
if resp.status < 200 or resp.status >= 300:
raise ClientException('Object POST failed', http_scheme=parsed.scheme,
http_host=conn.host, http_port=conn.port, http_path=path,
http_status=resp.status, http_reason=resp.reason)
http_status=resp.status, http_reason=resp.reason,
http_response_content=body)
def delete_object(url, token=None, container=None, name=None, http_conn=None,
@ -790,12 +803,12 @@ def delete_object(url, token=None, container=None, name=None, http_conn=None,
headers['X-Auth-Token'] = token
conn.request('DELETE', path, '', headers)
resp = conn.getresponse()
resp.read()
body = resp.read()
if resp.status < 200 or resp.status >= 300:
raise ClientException('Object DELETE failed',
http_scheme=parsed.scheme, http_host=conn.host,
http_port=conn.port, http_path=path, http_status=resp.status,
http_reason=resp.reason)
http_reason=resp.reason, http_response_content=body)
class Connection(object):

View File

@ -62,7 +62,7 @@ class ClientException(Exception):
def __init__(self, msg, http_scheme='', http_host='', http_port='',
http_path='', http_query='', http_status=0, http_reason='',
http_device=''):
http_device='', http_response_content=''):
Exception.__init__(self, msg)
self.msg = msg
self.http_scheme = http_scheme
@ -73,6 +73,7 @@ class ClientException(Exception):
self.http_status = http_status
self.http_reason = http_reason
self.http_device = http_device
self.http_response_content = http_response_content
def __str__(self):
a = self.msg
@ -102,6 +103,12 @@ class ClientException(Exception):
b = '%s: device %s' % (b, self.http_device)
else:
b = 'device %s' % self.http_device
if self.http_response_content:
if len(self.http_response_content) <= 60:
b += ' %s' % self.http_response_content
else:
b += ' [first 60 chars of response] %s' % \
self.http_response_content[:60]
return b and '%s: %s' % (a, b) or a
@ -211,11 +218,11 @@ def get_account(url, token, marker=None, limit=None, prefix=None,
for header, value in resp.getheaders():
resp_headers[header.lower()] = value
if resp.status < 200 or resp.status >= 300:
resp.read()
body = resp.read()
raise ClientException('Account GET failed', http_scheme=parsed.scheme,
http_host=conn.host, http_port=conn.port,
http_path=parsed.path, http_query=qs, http_status=resp.status,
http_reason=resp.reason)
http_reason=resp.reason, http_response_content=body)
if resp.status == 204:
resp.read()
return resp_headers, []
@ -240,12 +247,12 @@ def head_account(url, token, http_conn=None):
parsed, conn = http_connection(url)
conn.request('HEAD', parsed.path, '', {'X-Auth-Token': token})
resp = conn.getresponse()
resp.read()
body = resp.read()
if resp.status < 200 or resp.status >= 300:
raise ClientException('Account HEAD failed', http_scheme=parsed.scheme,
http_host=conn.host, http_port=conn.port,
http_path=parsed.path, http_status=resp.status,
http_reason=resp.reason)
http_reason=resp.reason, http_response_content=body)
resp_headers = {}
for header, value in resp.getheaders():
resp_headers[header.lower()] = value
@ -270,12 +277,13 @@ def post_account(url, token, headers, http_conn=None):
headers['X-Auth-Token'] = token
conn.request('POST', parsed.path, '', headers)
resp = conn.getresponse()
resp.read()
body = resp.read()
if resp.status < 200 or resp.status >= 300:
raise ClientException('Account POST failed',
http_scheme=parsed.scheme, http_host=conn.host,
http_port=conn.port, http_path=parsed.path,
http_status=resp.status, http_reason=resp.reason)
http_status=resp.status, http_reason=resp.reason,
http_response_content=body)
def get_container(url, token, container, marker=None, limit=None,
@ -329,11 +337,12 @@ def get_container(url, token, container, marker=None, limit=None,
conn.request('GET', '%s?%s' % (path, qs), '', {'X-Auth-Token': token})
resp = conn.getresponse()
if resp.status < 200 or resp.status >= 300:
resp.read()
body = resp.read()
raise ClientException('Container GET failed',
http_scheme=parsed.scheme, http_host=conn.host,
http_port=conn.port, http_path=path, http_query=qs,
http_status=resp.status, http_reason=resp.reason)
http_status=resp.status, http_reason=resp.reason,
http_response_content=body)
resp_headers = {}
for header, value in resp.getheaders():
resp_headers[header.lower()] = value
@ -366,12 +375,12 @@ def head_container(url, token, container, http_conn=None, headers=None):
req_headers.update(headers)
conn.request('HEAD', path, '', req_headers)
resp = conn.getresponse()
resp.read()
body = resp.read()
if resp.status < 200 or resp.status >= 300:
raise ClientException('Container HEAD failed',
http_scheme=parsed.scheme, http_host=conn.host,
http_port=conn.port, http_path=path, http_status=resp.status,
http_reason=resp.reason)
http_reason=resp.reason, http_response_content=body)
resp_headers = {}
for header, value in resp.getheaders():
resp_headers[header.lower()] = value
@ -400,12 +409,12 @@ def put_container(url, token, container, headers=None, http_conn=None):
headers['X-Auth-Token'] = token
conn.request('PUT', path, '', headers)
resp = conn.getresponse()
resp.read()
body = resp.read()
if resp.status < 200 or resp.status >= 300:
raise ClientException('Container PUT failed',
http_scheme=parsed.scheme, http_host=conn.host,
http_port=conn.port, http_path=path, http_status=resp.status,
http_reason=resp.reason)
http_reason=resp.reason, http_response_content=body)
def post_container(url, token, container, headers, http_conn=None):
@ -428,12 +437,12 @@ def post_container(url, token, container, headers, http_conn=None):
headers['X-Auth-Token'] = token
conn.request('POST', path, '', headers)
resp = conn.getresponse()
resp.read()
body = resp.read()
if resp.status < 200 or resp.status >= 300:
raise ClientException('Container POST failed',
http_scheme=parsed.scheme, http_host=conn.host,
http_port=conn.port, http_path=path, http_status=resp.status,
http_reason=resp.reason)
http_reason=resp.reason, http_response_content=body)
def delete_container(url, token, container, http_conn=None):
@ -454,12 +463,12 @@ def delete_container(url, token, container, http_conn=None):
path = '%s/%s' % (parsed.path, quote(container))
conn.request('DELETE', path, '', {'X-Auth-Token': token})
resp = conn.getresponse()
resp.read()
body = resp.read()
if resp.status < 200 or resp.status >= 300:
raise ClientException('Container DELETE failed',
http_scheme=parsed.scheme, http_host=conn.host,
http_port=conn.port, http_path=path, http_status=resp.status,
http_reason=resp.reason)
http_reason=resp.reason, http_response_content=body)
def get_object(url, token, container, name, http_conn=None,
@ -489,10 +498,11 @@ def get_object(url, token, container, name, http_conn=None,
conn.request('GET', path, '', {'X-Auth-Token': token})
resp = conn.getresponse()
if resp.status < 200 or resp.status >= 300:
resp.read()
body = resp.read()
raise ClientException('Object GET failed', http_scheme=parsed.scheme,
http_host=conn.host, http_port=conn.port, http_path=path,
http_status=resp.status, http_reason=resp.reason)
http_status=resp.status, http_reason=resp.reason,
http_response_content=body)
if resp_chunk_size:
def _object_body():
@ -530,11 +540,12 @@ def head_object(url, token, container, name, http_conn=None):
path = '%s/%s/%s' % (parsed.path, quote(container), quote(name))
conn.request('HEAD', path, '', {'X-Auth-Token': token})
resp = conn.getresponse()
resp.read()
body = resp.read()
if resp.status < 200 or resp.status >= 300:
raise ClientException('Object HEAD failed', http_scheme=parsed.scheme,
http_host=conn.host, http_port=conn.port, http_path=path,
http_status=resp.status, http_reason=resp.reason)
http_status=resp.status, http_reason=resp.reason,
http_response_content=body)
resp_headers = {}
for header, value in resp.getheaders():
resp_headers[header.lower()] = value
@ -624,11 +635,12 @@ def put_object(url, token=None, container=None, name=None, contents=None,
else:
conn.request('PUT', path, contents, headers)
resp = conn.getresponse()
resp.read()
body = resp.read()
if resp.status < 200 or resp.status >= 300:
raise ClientException('Object PUT failed', http_scheme=parsed.scheme,
http_host=conn.host, http_port=conn.port, http_path=path,
http_status=resp.status, http_reason=resp.reason)
http_status=resp.status, http_reason=resp.reason,
http_response_content=body)
return resp.getheader('etag', '').strip('"')
@ -653,11 +665,12 @@ def post_object(url, token, container, name, headers, http_conn=None):
headers['X-Auth-Token'] = token
conn.request('POST', path, '', headers)
resp = conn.getresponse()
resp.read()
body = resp.read()
if resp.status < 200 or resp.status >= 300:
raise ClientException('Object POST failed', http_scheme=parsed.scheme,
http_host=conn.host, http_port=conn.port, http_path=path,
http_status=resp.status, http_reason=resp.reason)
http_status=resp.status, http_reason=resp.reason,
http_response_content=body)
def delete_object(url, token=None, container=None, name=None, http_conn=None,
@ -695,12 +708,12 @@ def delete_object(url, token=None, container=None, name=None, http_conn=None,
headers['X-Auth-Token'] = token
conn.request('DELETE', path, '', headers)
resp = conn.getresponse()
resp.read()
body = resp.read()
if resp.status < 200 or resp.status >= 300:
raise ClientException('Object DELETE failed',
http_scheme=parsed.scheme, http_host=conn.host,
http_port=conn.port, http_path=path, http_status=resp.status,
http_reason=resp.reason)
http_reason=resp.reason, http_response_content=body)
class Connection(object):

View File

@ -170,9 +170,15 @@ class TestHeadAccount(MockHttpTest):
self.assertEquals(type(value), dict)
def test_server_error(self):
c.http_connection = self.fake_http_connection(500)
body = 'c' * 65
c.http_connection = self.fake_http_connection(500, body=body)
self.assertRaises(c.ClientException, c.head_account,
'http://www.tests.com', 'asdf')
try:
value = c.head_account('http://www.tests.com', 'asdf')
except c.ClientException as e:
new_body = "[first 60 chars of response] " + body[0:60]
self.assertEquals(e.__str__()[-89:], new_body)
class TestGetContainer(MockHttpTest):
@ -186,10 +192,15 @@ class TestGetContainer(MockHttpTest):
class TestHeadContainer(MockHttpTest):
def test_server_error(self):
c.http_connection = self.fake_http_connection(500)
body = 'c' * 60
c.http_connection = self.fake_http_connection(500, body=body)
self.assertRaises(c.ClientException, c.head_container,
'http://www.test.com', 'asdf', 'asdf',
)
try:
value = c.head_container('http://www.test.com', 'asdf', 'asdf')
except c.ClientException as e:
self.assertEquals(e.http_response_content, body)
class TestPutContainer(MockHttpTest):
@ -199,6 +210,17 @@ class TestPutContainer(MockHttpTest):
value = c.put_container('http://www.test.com', 'asdf', 'asdf')
self.assertEquals(value, None)
def test_server_error(self):
body = 'c' * 60
c.http_connection = self.fake_http_connection(500, body=body)
self.assertRaises(c.ClientException, c.put_container,
'http://www.test.com', 'asdf', 'asdf',
)
try:
value = c.put_container('http://www.test.com', 'asdf', 'asdf')
except c.ClientException as e:
self.assertEquals(e.http_response_content, body)
class TestDeleteContainer(MockHttpTest):
@ -233,9 +255,14 @@ class TestPutObject(MockHttpTest):
self.assertTrue(isinstance(value, basestring))
def test_server_error(self):
c.http_connection = self.fake_http_connection(500)
body = 'c' * 60
c.http_connection = self.fake_http_connection(500, body=body)
args = ('http://www.test.com', 'asdf', 'asdf', 'asdf', 'asdf')
self.assertRaises(c.ClientException, c.put_object, *args)
try:
value = c.put_object(*args)
except c.ClientException as e:
self.assertEquals(e.http_response_content, body)
class TestPostObject(MockHttpTest):
@ -246,9 +273,14 @@ class TestPostObject(MockHttpTest):
value = c.post_object(*args)
def test_server_error(self):
c.http_connection = self.fake_http_connection(500)
self.assertRaises(c.ClientException, c.post_object,
'http://www.test.com', 'asdf', 'asdf', 'asdf', {})
body = 'c' * 60
c.http_connection = self.fake_http_connection(500, body=body)
args = ('http://www.test.com', 'asdf', 'asdf', 'asdf', {})
self.assertRaises(c.ClientException, c.post_object, *args)
try:
value = c.post_object(*args)
except c.ClientException as e:
self.assertEquals(e.http_response_content, body)
class TestDeleteObject(MockHttpTest):