Fixed _error_checker in rest client
Restclient's method '_error_checker' for response codes 500 and 501 gets key error exception when 'resp_body' is a string and passes conditions for containing of keys. Also added fix to rarely raised Exceptions after separation main and base exceptions for two modules. Closes-Bug: #1280767 Closes-Bug: #1289190 Partially-implements: bp unit-tests Change-Id: I4b909d008940f8a96efc922daac64a086819c78a
This commit is contained in:
parent
be392f2d7c
commit
6cb6d190f4
@ -409,7 +409,7 @@ class RestClient(object):
|
||||
elif ctype.lower() in TXT_ENC:
|
||||
parse_resp = False
|
||||
else:
|
||||
raise exceptions.RestClientException(str(resp.status))
|
||||
raise exceptions.InvalidContentType(str(resp.status))
|
||||
|
||||
if resp.status == 401 or resp.status == 403:
|
||||
raise exceptions.Unauthorized()
|
||||
@ -451,25 +451,26 @@ class RestClient(object):
|
||||
# exception.
|
||||
raise exceptions.InvalidHTTPResponseBody(message)
|
||||
else:
|
||||
# I'm seeing both computeFault
|
||||
# and cloudServersFault come back.
|
||||
# Will file a bug to fix, but leave as is for now.
|
||||
if 'cloudServersFault' in resp_body:
|
||||
message = resp_body['cloudServersFault']['message']
|
||||
elif 'computeFault' in resp_body:
|
||||
message = resp_body['computeFault']['message']
|
||||
elif 'error' in resp_body: # Keystone errors
|
||||
message = resp_body['error']['message']
|
||||
raise exceptions.IdentityError(message)
|
||||
elif 'message' in resp_body:
|
||||
message = resp_body['message']
|
||||
if isinstance(resp_body, dict):
|
||||
# I'm seeing both computeFault
|
||||
# and cloudServersFault come back.
|
||||
# Will file a bug to fix, but leave as is for now.
|
||||
if 'cloudServersFault' in resp_body:
|
||||
message = resp_body['cloudServersFault']['message']
|
||||
elif 'computeFault' in resp_body:
|
||||
message = resp_body['computeFault']['message']
|
||||
elif 'error' in resp_body: # Keystone errors
|
||||
message = resp_body['error']['message']
|
||||
raise exceptions.IdentityError(message)
|
||||
elif 'message' in resp_body:
|
||||
message = resp_body['message']
|
||||
else:
|
||||
message = resp_body
|
||||
|
||||
raise exceptions.ServerFault(message)
|
||||
|
||||
if resp.status >= 400:
|
||||
if parse_resp:
|
||||
resp_body = self._parse_resp(resp_body)
|
||||
raise exceptions.RestClientException(str(resp.status))
|
||||
raise exceptions.UnexpectedResponseCode(str(resp.status))
|
||||
|
||||
def is_absolute_limit(self, resp, resp_body):
|
||||
if (not isinstance(resp_body, collections.Mapping) or
|
||||
|
@ -146,3 +146,11 @@ class ResponseWithEntity(base.RFCViolation):
|
||||
|
||||
class InvalidHTTPResponseBody(base.RestClientException):
|
||||
message = "HTTP response body is invalid json or xml"
|
||||
|
||||
|
||||
class InvalidContentType(base.RestClientException):
|
||||
message = "Invalid content type provided"
|
||||
|
||||
|
||||
class UnexpectedResponseCode(base.RestClientException):
|
||||
message = "Unexpected response code received"
|
||||
|
@ -230,3 +230,114 @@ class TestRestClientParseRespJSON(TestRestClientParseRespXML):
|
||||
data = {"one_top_key": "not_list_or_dict_value"}
|
||||
body = self.rest_client._parse_resp(json.dumps(data))
|
||||
self.assertEqual(data, body)
|
||||
|
||||
|
||||
class TestRestClientErrorCheckerJSON(base.TestCase):
|
||||
c_type = "application/json"
|
||||
|
||||
def set_data(self, r_code, enc=None, r_body=None):
|
||||
if enc is None:
|
||||
enc = self.c_type
|
||||
resp_dict = {'status': r_code, 'content-type': enc}
|
||||
resp = httplib2.Response(resp_dict)
|
||||
data = {
|
||||
"method": "fake_method",
|
||||
"url": "fake_url",
|
||||
"headers": "fake_headers",
|
||||
"body": "fake_body",
|
||||
"resp": resp,
|
||||
"resp_body": '{"resp_body": "fake_resp_body"}',
|
||||
}
|
||||
if r_body is not None:
|
||||
data.update({"resp_body": r_body})
|
||||
return data
|
||||
|
||||
def setUp(self):
|
||||
super(TestRestClientErrorCheckerJSON, self).setUp()
|
||||
self.stubs.Set(config, 'TempestConfigPrivate', fake_config.FakeConfig)
|
||||
self.rest_client = rest_client.RestClient(
|
||||
fake_auth_provider.FakeAuthProvider())
|
||||
|
||||
def test_response_less_than_400(self):
|
||||
self.rest_client._error_checker(**self.set_data("399"))
|
||||
|
||||
def test_response_400(self):
|
||||
self.assertRaises(exceptions.BadRequest,
|
||||
self.rest_client._error_checker,
|
||||
**self.set_data("400"))
|
||||
|
||||
def test_response_401(self):
|
||||
self.assertRaises(exceptions.Unauthorized,
|
||||
self.rest_client._error_checker,
|
||||
**self.set_data("401"))
|
||||
|
||||
def test_response_403(self):
|
||||
self.assertRaises(exceptions.Unauthorized,
|
||||
self.rest_client._error_checker,
|
||||
**self.set_data("403"))
|
||||
|
||||
def test_response_404(self):
|
||||
self.assertRaises(exceptions.NotFound,
|
||||
self.rest_client._error_checker,
|
||||
**self.set_data("404"))
|
||||
|
||||
def test_response_409(self):
|
||||
self.assertRaises(exceptions.Conflict,
|
||||
self.rest_client._error_checker,
|
||||
**self.set_data("409"))
|
||||
|
||||
def test_response_413(self):
|
||||
self.assertRaises(exceptions.OverLimit,
|
||||
self.rest_client._error_checker,
|
||||
**self.set_data("413"))
|
||||
|
||||
def test_response_422(self):
|
||||
self.assertRaises(exceptions.UnprocessableEntity,
|
||||
self.rest_client._error_checker,
|
||||
**self.set_data("422"))
|
||||
|
||||
def test_response_500_with_text(self):
|
||||
# _parse_resp is expected to return 'str'
|
||||
self.assertRaises(exceptions.ServerFault,
|
||||
self.rest_client._error_checker,
|
||||
**self.set_data("500"))
|
||||
|
||||
def test_response_501_with_text(self):
|
||||
self.assertRaises(exceptions.ServerFault,
|
||||
self.rest_client._error_checker,
|
||||
**self.set_data("501"))
|
||||
|
||||
def test_response_500_with_dict(self):
|
||||
r_body = '{"resp_body": {"err": "fake_resp_body"}}'
|
||||
self.assertRaises(exceptions.ServerFault,
|
||||
self.rest_client._error_checker,
|
||||
**self.set_data("500", r_body=r_body))
|
||||
|
||||
def test_response_501_with_dict(self):
|
||||
r_body = '{"resp_body": {"err": "fake_resp_body"}}'
|
||||
self.assertRaises(exceptions.ServerFault,
|
||||
self.rest_client._error_checker,
|
||||
**self.set_data("501", r_body=r_body))
|
||||
|
||||
def test_response_bigger_than_400(self):
|
||||
# Any response code, that bigger than 400, and not in
|
||||
# (401, 403, 404, 409, 413, 422, 500, 501)
|
||||
self.assertRaises(exceptions.UnexpectedResponseCode,
|
||||
self.rest_client._error_checker,
|
||||
**self.set_data("402"))
|
||||
|
||||
|
||||
class TestRestClientErrorCheckerXML(TestRestClientErrorCheckerJSON):
|
||||
c_type = "application/xml"
|
||||
|
||||
|
||||
class TestRestClientErrorCheckerTEXT(TestRestClientErrorCheckerJSON):
|
||||
c_type = "text/plain"
|
||||
|
||||
def test_fake_content_type(self):
|
||||
# This test is required only in one exemplar
|
||||
# Any response code, that bigger than 400, and not in
|
||||
# (401, 403, 404, 409, 413, 422, 500, 501)
|
||||
self.assertRaises(exceptions.InvalidContentType,
|
||||
self.rest_client._error_checker,
|
||||
**self.set_data("405", enc="fake_enc"))
|
||||
|
Loading…
Reference in New Issue
Block a user