Don't lose AttributeError in API Wrappers
Instead of (implicitly) catching the AttributeError, and later creating and raising a new one, we just re-raise the original exception. This way all the information from the original is retained, including the name of the actual object on which it happened. Change-Id: Idc0c5a8ed5dfca6a8724e393c220baf9960564ed Closes-bug: #1274097
This commit is contained in:
parent
f96c049cda
commit
20b414db2f
@ -73,21 +73,19 @@ class APIResourceWrapper(object):
|
|||||||
api object as the only argument to the constructor
|
api object as the only argument to the constructor
|
||||||
"""
|
"""
|
||||||
_attrs = []
|
_attrs = []
|
||||||
|
_apiresource = None # Make sure _apiresource is there even in __init__.
|
||||||
|
|
||||||
def __init__(self, apiresource):
|
def __init__(self, apiresource):
|
||||||
self._apiresource = apiresource
|
self._apiresource = apiresource
|
||||||
|
|
||||||
def __getattr__(self, attr):
|
def __getattribute__(self, attr):
|
||||||
if attr in self._attrs:
|
try:
|
||||||
|
return object.__getattribute__(self, attr)
|
||||||
|
except AttributeError:
|
||||||
|
if attr not in self._attrs:
|
||||||
|
raise
|
||||||
# __getattr__ won't find properties
|
# __getattr__ won't find properties
|
||||||
return self._apiresource.__getattribute__(attr)
|
return getattr(self._apiresource, attr)
|
||||||
else:
|
|
||||||
msg = ('Attempted to access unknown attribute "%s" on '
|
|
||||||
'APIResource object of type "%s" wrapping resource of '
|
|
||||||
'type "%s".') % (attr, self.__class__,
|
|
||||||
self._apiresource.__class__)
|
|
||||||
LOG.debug(exceptions.error_color(msg))
|
|
||||||
raise AttributeError(attr)
|
|
||||||
|
|
||||||
def __repr__(self):
|
def __repr__(self):
|
||||||
return "<%s: %s>" % (self.__class__.__name__,
|
return "<%s: %s>" % (self.__class__.__name__,
|
||||||
@ -106,28 +104,30 @@ class APIDictWrapper(object):
|
|||||||
Attribute access is the preferred method of access, to be
|
Attribute access is the preferred method of access, to be
|
||||||
consistent with api resource objects from novaclient.
|
consistent with api resource objects from novaclient.
|
||||||
"""
|
"""
|
||||||
|
|
||||||
|
_apidict = {} # Make sure _apidict is there even in __init__.
|
||||||
|
|
||||||
def __init__(self, apidict):
|
def __init__(self, apidict):
|
||||||
self._apidict = apidict
|
self._apidict = apidict
|
||||||
|
|
||||||
def __getattr__(self, attr):
|
def __getattribute__(self, attr):
|
||||||
try:
|
try:
|
||||||
|
return object.__getattribute__(self, attr)
|
||||||
|
except AttributeError:
|
||||||
|
if attr not in self._apidict:
|
||||||
|
raise
|
||||||
return self._apidict[attr]
|
return self._apidict[attr]
|
||||||
except KeyError:
|
|
||||||
msg = 'Unknown attribute "%(attr)s" on APIResource object ' \
|
|
||||||
'of type "%(cls)s"' % {'attr': attr, 'cls': self.__class__}
|
|
||||||
LOG.debug(exceptions.error_color(msg))
|
|
||||||
raise AttributeError(msg)
|
|
||||||
|
|
||||||
def __getitem__(self, item):
|
def __getitem__(self, item):
|
||||||
try:
|
try:
|
||||||
return self.__getattr__(item)
|
return getattr(self, item)
|
||||||
except AttributeError as e:
|
except AttributeError as e:
|
||||||
# caller is expecting a KeyError
|
# caller is expecting a KeyError
|
||||||
raise KeyError(e)
|
raise KeyError(e)
|
||||||
|
|
||||||
def get(self, item, default=None):
|
def get(self, item, default=None):
|
||||||
try:
|
try:
|
||||||
return self.__getattr__(item)
|
return getattr(self, item)
|
||||||
except AttributeError:
|
except AttributeError:
|
||||||
return default
|
return default
|
||||||
|
|
||||||
|
@ -122,7 +122,7 @@ class NetworkApiNovaFloatingIpTests(NetworkApiNovaTestBase):
|
|||||||
ret = api.network.tenant_floating_ip_list(self.request)
|
ret = api.network.tenant_floating_ip_list(self.request)
|
||||||
for r, e in zip(ret, fips):
|
for r, e in zip(ret, fips):
|
||||||
for attr in ['id', 'ip', 'pool', 'fixed_ip', 'instance_id']:
|
for attr in ['id', 'ip', 'pool', 'fixed_ip', 'instance_id']:
|
||||||
self.assertEqual(r.__getattr__(attr), e.__getattr__(attr))
|
self.assertEqual(getattr(r, attr), getattr(e, attr))
|
||||||
self.assertEqual(r.port_id, e.instance_id)
|
self.assertEqual(r.port_id, e.instance_id)
|
||||||
|
|
||||||
def test_floating_ip_get(self):
|
def test_floating_ip_get(self):
|
||||||
@ -134,7 +134,7 @@ class NetworkApiNovaFloatingIpTests(NetworkApiNovaTestBase):
|
|||||||
|
|
||||||
ret = api.network.tenant_floating_ip_get(self.request, fip.id)
|
ret = api.network.tenant_floating_ip_get(self.request, fip.id)
|
||||||
for attr in ['id', 'ip', 'pool', 'fixed_ip', 'instance_id']:
|
for attr in ['id', 'ip', 'pool', 'fixed_ip', 'instance_id']:
|
||||||
self.assertEqual(ret.__getattr__(attr), fip.__getattr__(attr))
|
self.assertEqual(getattr(ret, attr), getattr(fip, attr))
|
||||||
self.assertEqual(ret.port_id, fip.instance_id)
|
self.assertEqual(ret.port_id, fip.instance_id)
|
||||||
|
|
||||||
def test_floating_ip_allocate(self):
|
def test_floating_ip_allocate(self):
|
||||||
@ -147,7 +147,7 @@ class NetworkApiNovaFloatingIpTests(NetworkApiNovaTestBase):
|
|||||||
|
|
||||||
ret = api.network.tenant_floating_ip_allocate(self.request, pool_name)
|
ret = api.network.tenant_floating_ip_allocate(self.request, pool_name)
|
||||||
for attr in ['id', 'ip', 'pool', 'fixed_ip', 'instance_id']:
|
for attr in ['id', 'ip', 'pool', 'fixed_ip', 'instance_id']:
|
||||||
self.assertEqual(ret.__getattr__(attr), fip.__getattr__(attr))
|
self.assertEqual(getattr(ret, attr), getattr(fip, attr))
|
||||||
self.assertEqual(ret.port_id, fip.instance_id)
|
self.assertEqual(ret.port_id, fip.instance_id)
|
||||||
|
|
||||||
def test_floating_ip_release(self):
|
def test_floating_ip_release(self):
|
||||||
@ -410,7 +410,7 @@ class NetworkApiNeutronFloatingIpTests(NetworkApiNeutronTestBase):
|
|||||||
|
|
||||||
rets = api.network.floating_ip_pools_list(self.request)
|
rets = api.network.floating_ip_pools_list(self.request)
|
||||||
for attr in ['id', 'name']:
|
for attr in ['id', 'name']:
|
||||||
self.assertEqual([p.__getattr__(attr) for p in rets],
|
self.assertEqual([getattr(p, attr) for p in rets],
|
||||||
[p[attr] for p in ext_nets])
|
[p[attr] for p in ext_nets])
|
||||||
|
|
||||||
def test_floating_ip_list(self):
|
def test_floating_ip_list(self):
|
||||||
@ -427,7 +427,7 @@ class NetworkApiNeutronFloatingIpTests(NetworkApiNeutronTestBase):
|
|||||||
self.assertEqual(len(fips), len(rets))
|
self.assertEqual(len(fips), len(rets))
|
||||||
for ret, exp in zip(rets, fips):
|
for ret, exp in zip(rets, fips):
|
||||||
for attr in ['id', 'ip', 'pool', 'fixed_ip', 'port_id']:
|
for attr in ['id', 'ip', 'pool', 'fixed_ip', 'port_id']:
|
||||||
self.assertEqual(ret.__getattr__(attr), exp[attr])
|
self.assertEqual(getattr(ret, attr), exp[attr])
|
||||||
if exp['port_id']:
|
if exp['port_id']:
|
||||||
dev_id = assoc_port['device_id'] if exp['port_id'] else None
|
dev_id = assoc_port['device_id'] if exp['port_id'] else None
|
||||||
self.assertEqual(ret.instance_id, dev_id)
|
self.assertEqual(ret.instance_id, dev_id)
|
||||||
@ -442,7 +442,7 @@ class NetworkApiNeutronFloatingIpTests(NetworkApiNeutronTestBase):
|
|||||||
|
|
||||||
ret = api.network.tenant_floating_ip_get(self.request, fip['id'])
|
ret = api.network.tenant_floating_ip_get(self.request, fip['id'])
|
||||||
for attr in ['id', 'ip', 'pool', 'fixed_ip', 'port_id']:
|
for attr in ['id', 'ip', 'pool', 'fixed_ip', 'port_id']:
|
||||||
self.assertEqual(ret.__getattr__(attr), fip[attr])
|
self.assertEqual(getattr(ret, attr), fip[attr])
|
||||||
self.assertEqual(ret.instance_id, assoc_port['device_id'])
|
self.assertEqual(ret.instance_id, assoc_port['device_id'])
|
||||||
|
|
||||||
def test_floating_ip_get_unassociated(self):
|
def test_floating_ip_get_unassociated(self):
|
||||||
@ -452,7 +452,7 @@ class NetworkApiNeutronFloatingIpTests(NetworkApiNeutronTestBase):
|
|||||||
|
|
||||||
ret = api.network.tenant_floating_ip_get(self.request, fip['id'])
|
ret = api.network.tenant_floating_ip_get(self.request, fip['id'])
|
||||||
for attr in ['id', 'ip', 'pool', 'fixed_ip', 'port_id']:
|
for attr in ['id', 'ip', 'pool', 'fixed_ip', 'port_id']:
|
||||||
self.assertEqual(ret.__getattr__(attr), fip[attr])
|
self.assertEqual(getattr(ret, attr), fip[attr])
|
||||||
self.assertIsNone(ret.instance_id)
|
self.assertIsNone(ret.instance_id)
|
||||||
|
|
||||||
def test_floating_ip_allocate(self):
|
def test_floating_ip_allocate(self):
|
||||||
@ -468,7 +468,7 @@ class NetworkApiNeutronFloatingIpTests(NetworkApiNeutronTestBase):
|
|||||||
ret = api.network.tenant_floating_ip_allocate(self.request,
|
ret = api.network.tenant_floating_ip_allocate(self.request,
|
||||||
ext_net['id'])
|
ext_net['id'])
|
||||||
for attr in ['id', 'ip', 'pool', 'fixed_ip', 'port_id']:
|
for attr in ['id', 'ip', 'pool', 'fixed_ip', 'port_id']:
|
||||||
self.assertEqual(ret.__getattr__(attr), fip[attr])
|
self.assertEqual(getattr(ret, attr), fip[attr])
|
||||||
self.assertIsNone(ret.instance_id)
|
self.assertIsNone(ret.instance_id)
|
||||||
|
|
||||||
def test_floating_ip_release(self):
|
def test_floating_ip_release(self):
|
||||||
|
Loading…
Reference in New Issue
Block a user