Split security group list operations
Security groups can come from either nova or neutron or not be available by the vendor. This uses a new flag from os-client-config to determine where we should get the list from. Also, a new exception is added for features that are not supported. This required a minimum version bump in os-client-config. Change-Id: I4474341ebc255700a06247846c6350981437e8ae
This commit is contained in:
parent
3fef40f07e
commit
a4e9d5cfc0
@ -2,7 +2,7 @@ pbr>=0.11,<2.0
|
||||
|
||||
bunch
|
||||
jsonpatch
|
||||
os-client-config>=1.0.0
|
||||
os-client-config>=1.2.0
|
||||
six
|
||||
|
||||
python-novaclient>=2.21.0
|
||||
|
@ -238,6 +238,8 @@ class OpenStackCloud(object):
|
||||
self.api_versions = _get_service_values(kwargs, 'api_version')
|
||||
self.image_api_use_tasks = image_api_use_tasks
|
||||
|
||||
self.secgroup_source = kwargs.get('secgroup_source', None)
|
||||
|
||||
(self.verify, self.cert) = _ssl_args(verify, cacert, cert, key)
|
||||
|
||||
self._cache = cache.make_region(
|
||||
@ -804,15 +806,58 @@ class OpenStackCloud(object):
|
||||
"Error fetching flavor list: %s" % e)
|
||||
|
||||
def list_security_groups(self):
|
||||
try:
|
||||
return meta.obj_list_to_dict(
|
||||
self.manager.submitTask(_tasks.SecurityGroupList())
|
||||
# Handle neutron security groups
|
||||
if self.secgroup_source == 'neutron':
|
||||
# Neutron returns dicts, so no need to convert objects here.
|
||||
try:
|
||||
groups = self.manager.submitTask(
|
||||
_tasks.NeutronSecurityGroupList())['security_groups']
|
||||
except Exception as e:
|
||||
self.log.debug(
|
||||
"neutron could not list security groups: {message}".format(
|
||||
message=str(e)),
|
||||
exc_info=True)
|
||||
raise OpenStackCloudException(
|
||||
"Error fetching security group list"
|
||||
)
|
||||
return groups
|
||||
|
||||
# Handle nova security groups
|
||||
elif self.secgroup_source == 'nova':
|
||||
try:
|
||||
groups = meta.obj_list_to_dict(
|
||||
self.manager.submitTask(_tasks.NovaSecurityGroupList())
|
||||
)
|
||||
except Exception as e:
|
||||
self.log.debug(
|
||||
"nova could not list security groups: {message}".format(
|
||||
message=str(e)),
|
||||
exc_info=True)
|
||||
raise OpenStackCloudException(
|
||||
"Error fetching security group list"
|
||||
)
|
||||
# Make Nova data look like Neutron data. This doesn't make them
|
||||
# look exactly the same, but pretty close.
|
||||
return [{'id': g['id'],
|
||||
'name': g['name'],
|
||||
'description': g['description'],
|
||||
'security_group_rules': [{
|
||||
'id': r['id'],
|
||||
'direction': 'ingress',
|
||||
'ethertype': 'IPv4',
|
||||
'port_range_min': r['from_port'],
|
||||
'port_range_max': r['to_port'],
|
||||
'protocol': r['ip_protocol'],
|
||||
'remote_ip_prefix': r['ip_range'].get('cidr', None),
|
||||
'security_group_id': r['parent_group_id'],
|
||||
} for r in g['rules']]
|
||||
} for g in groups]
|
||||
|
||||
# Security groups not supported
|
||||
else:
|
||||
raise OpenStackCloudUnavailableFeature(
|
||||
"Unavailable feature: security groups"
|
||||
)
|
||||
except Exception as e:
|
||||
self.log.debug(
|
||||
"security group list failed: %s" % e, exc_info=True)
|
||||
raise OpenStackCloudException(
|
||||
"Error fetching security group list: %s" % e)
|
||||
|
||||
def list_servers(self):
|
||||
try:
|
||||
|
@ -192,7 +192,12 @@ class VolumeAttach(task_manager.Task):
|
||||
client.nova_client.volumes.create_server_volume(**self.args)
|
||||
|
||||
|
||||
class SecurityGroupList(task_manager.Task):
|
||||
class NeutronSecurityGroupList(task_manager.Task):
|
||||
def main(self, client):
|
||||
return client.neutron_client.list_security_groups()
|
||||
|
||||
|
||||
class NovaSecurityGroupList(task_manager.Task):
|
||||
def main(self, client):
|
||||
return client.nova_client.security_groups.list()
|
||||
|
||||
|
@ -38,3 +38,7 @@ class OpenStackCloudUnavailableService(OpenStackCloudException):
|
||||
|
||||
class OpenStackCloudUnavailableExtension(OpenStackCloudException):
|
||||
pass
|
||||
|
||||
|
||||
class OpenStackCloudUnavailableFeature(OpenStackCloudException):
|
||||
pass
|
||||
|
@ -324,6 +324,31 @@ class TestShade(base.TestCase):
|
||||
flavor2 = self.cloud.get_flavor(1)
|
||||
self.assertEquals(vanilla, flavor2)
|
||||
|
||||
@mock.patch.object(shade.OpenStackCloud, 'neutron_client')
|
||||
@mock.patch.object(shade.OpenStackCloud, 'nova_client')
|
||||
def test_list_security_groups_neutron(self, mock_nova, mock_neutron):
|
||||
self.cloud.secgroup_source = 'neutron'
|
||||
self.cloud.list_security_groups()
|
||||
self.assertTrue(mock_neutron.list_security_groups.called)
|
||||
self.assertFalse(mock_nova.security_groups.list.called)
|
||||
|
||||
@mock.patch.object(shade.OpenStackCloud, 'neutron_client')
|
||||
@mock.patch.object(shade.OpenStackCloud, 'nova_client')
|
||||
def test_list_security_groups_nova(self, mock_nova, mock_neutron):
|
||||
self.cloud.secgroup_source = 'nova'
|
||||
self.cloud.list_security_groups()
|
||||
self.assertFalse(mock_neutron.list_security_groups.called)
|
||||
self.assertTrue(mock_nova.security_groups.list.called)
|
||||
|
||||
@mock.patch.object(shade.OpenStackCloud, 'neutron_client')
|
||||
@mock.patch.object(shade.OpenStackCloud, 'nova_client')
|
||||
def test_list_security_groups_none(self, mock_nova, mock_neutron):
|
||||
self.cloud.secgroup_source = None
|
||||
self.assertRaises(shade.OpenStackCloudUnavailableFeature,
|
||||
self.cloud.list_security_groups)
|
||||
self.assertFalse(mock_neutron.list_security_groups.called)
|
||||
self.assertFalse(mock_nova.security_groups.list.called)
|
||||
|
||||
|
||||
class TestShadeOperator(base.TestCase):
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user