diff options
author | Gabriel Hurley <gabriel@strikeawe.com> | 2011-10-25 16:50:08 -0700 |
---|---|---|
committer | Gabriel Hurley <gabriel@strikeawe.com> | 2011-10-25 16:50:08 -0700 |
commit | 17f6b83ee6157371104b065d7fb9cb6e5b03c386 (patch) | |
tree | 61e4b41e2edf001f6023b305f37d3c61131e9708 /keystoneclient/exceptions.py | |
download | python-keystoneclient-17f6b83ee6157371104b065d7fb9cb6e5b03c386.tar.gz |
Initial commit.
Diffstat (limited to 'keystoneclient/exceptions.py')
-rw-r--r-- | keystoneclient/exceptions.py | 129 |
1 files changed, 129 insertions, 0 deletions
diff --git a/keystoneclient/exceptions.py b/keystoneclient/exceptions.py new file mode 100644 index 0000000..8f8ea57 --- /dev/null +++ b/keystoneclient/exceptions.py @@ -0,0 +1,129 @@ +# Copyright 2010 Jacob Kaplan-Moss +# Copyright 2011 Nebula, Inc. +""" +Exception definitions. +""" + + +class CommandError(Exception): + pass + + +class AuthorizationFailure(Exception): + pass + + +class NoTokenLookupException(Exception): + """This form of authentication does not support looking up + endpoints from an existing token.""" + pass + + +class EndpointNotFound(Exception): + """Could not find Service or Region in Service Catalog.""" + pass + + +class ClientException(Exception): + """ + The base exception class for all exceptions this library raises. + """ + def __init__(self, code, message=None, details=None): + self.code = code + self.message = message or self.__class__.message + self.details = details + + def __str__(self): + return "%s (HTTP %s)" % (self.message, self.code) + + +class BadRequest(ClientException): + """ + HTTP 400 - Bad request: you sent some malformed data. + """ + http_status = 400 + message = "Bad request" + + +class Unauthorized(ClientException): + """ + HTTP 401 - Unauthorized: bad credentials. + """ + http_status = 401 + message = "Unauthorized" + + +class Forbidden(ClientException): + """ + HTTP 403 - Forbidden: your credentials don't give you access to this + resource. + """ + http_status = 403 + message = "Forbidden" + + +class NotFound(ClientException): + """ + HTTP 404 - Not found + """ + http_status = 404 + message = "Not found" + + +class Conflict(ClientException): + """ + HTTP 409 - Conflict + """ + http_status = 409 + message = "Conflict" + + +class OverLimit(ClientException): + """ + HTTP 413 - Over limit: you're over the API limits for this time period. + """ + http_status = 413 + message = "Over limit" + + +# NotImplemented is a python keyword. +class HTTPNotImplemented(ClientException): + """ + HTTP 501 - Not Implemented: the server does not support this operation. + """ + http_status = 501 + message = "Not Implemented" + + +# In Python 2.4 Exception is old-style and thus doesn't have a __subclasses__() +# so we can do this: +# _code_map = dict((c.http_status, c) +# for c in ClientException.__subclasses__()) +# +# Instead, we have to hardcode it: +_code_map = dict((c.http_status, c) for c in [BadRequest, Unauthorized, + Forbidden, NotFound, OverLimit, HTTPNotImplemented]) + + +def from_response(response, body): + """ + Return an instance of an ClientException or subclass + based on an httplib2 response. + + Usage:: + + resp, body = http.request(...) + if resp.status != 200: + raise exception_from_response(resp, body) + """ + cls = _code_map.get(response.status, ClientException) + if body: + message = "n/a" + details = "n/a" + if hasattr(body, 'keys'): + error = body[body.keys()[0]] + message = error.get('message', None) + details = error.get('details', None) + return cls(code=response.status, message=message, details=details) + else: + return cls(code=response.status) |