From c64678868e178f955a465dda6d16623368c6b924 Mon Sep 17 00:00:00 2001 From: Anindita Das Date: Thu, 29 Sep 2016 17:58:26 +0000 Subject: [PATCH] Add support for network Service Flavor Profile This patch set adds the support for the retrieve, update, create and delete for the network Flavor Profile Change-Id: I653ea0ba041e286941841701ea0c6e0f70e9e568 Partially-Implements: blueprint neutron-client-flavors --- doc/source/users/resources/network/index.rst | 1 + .../resources/network/v2/service_profile.rst | 12 +++ openstack/network/v2/_proxy.py | 90 +++++++++++++++++++ openstack/network/v2/service_profile.py | 40 +++++++++ .../network/v2/test_service_profile.py | 64 +++++++++++++ openstack/tests/unit/network/v2/test_proxy.py | 25 ++++++ .../unit/network/v2/test_service_profile.py | 59 ++++++++++++ 7 files changed, 291 insertions(+) create mode 100644 doc/source/users/resources/network/v2/service_profile.rst create mode 100644 openstack/network/v2/service_profile.py create mode 100644 openstack/tests/functional/network/v2/test_service_profile.py create mode 100644 openstack/tests/unit/network/v2/test_service_profile.py diff --git a/doc/source/users/resources/network/index.rst b/doc/source/users/resources/network/index.rst index b7410783..6926f784 100644 --- a/doc/source/users/resources/network/index.rst +++ b/doc/source/users/resources/network/index.rst @@ -31,6 +31,7 @@ Network Resources v2/security_group v2/security_group_rule v2/segment + v2/service_profile v2/service_provider v2/subnet v2/subnet_pool diff --git a/doc/source/users/resources/network/v2/service_profile.rst b/doc/source/users/resources/network/v2/service_profile.rst new file mode 100644 index 00000000..c1c01302 --- /dev/null +++ b/doc/source/users/resources/network/v2/service_profile.rst @@ -0,0 +1,12 @@ +openstack.network.v2.service_profile +==================================== + +.. automodule:: openstack.network.v2.service_profile + +The ServiceProfile Class +------------------------ + +The ``ServiceProfile`` class inherits from :class:`~openstack.resource.Resource`. + +.. autoclass:: openstack.network.v2.service_profile.ServiceProfile + :members: diff --git a/openstack/network/v2/_proxy.py b/openstack/network/v2/_proxy.py index bd30c280..c6d769c3 100644 --- a/openstack/network/v2/_proxy.py +++ b/openstack/network/v2/_proxy.py @@ -40,6 +40,7 @@ from openstack.network.v2 import router as _router from openstack.network.v2 import security_group as _security_group from openstack.network.v2 import security_group_rule as _security_group_rule from openstack.network.v2 import segment as _segment +from openstack.network.v2 import service_profile as _service_profile from openstack.network.v2 import service_provider as _service_provider from openstack.network.v2 import subnet as _subnet from openstack.network.v2 import subnet_pool as _subnet_pool @@ -2307,6 +2308,95 @@ class Proxy(proxy.BaseProxy): return self._list(_service_provider.ServiceProvider, paginated=False, **query) + def create_service_profile(self, **attrs): + """Create a new network service flavor profile from attributes + + :param dict attrs: Keyword arguments which will be used to create + a :class:`~openstack.network.v2.service_profile + .ServiceProfile`, + comprised of the properties on the ServiceProfile + class. + + :returns: The results of service profile creation + :rtype: :class:`~openstack.network.v2.service_profile.ServiceProfile` + """ + return self._create(_service_profile.ServiceProfile, **attrs) + + def delete_service_profile(self, service_profile, ignore_missing=True): + """Delete a network service flavor profile + + :param service_profile: The value can be either the ID of a service + profile or a + :class:`~openstack.network.v2.service_profile + .ServiceProfile` instance. + :param bool ignore_missing: When set to ``False`` + :class:`~openstack.exceptions.ResourceNotFound` will be + raised when the service profile does not exist. + When set to ``True``, no exception will be set when + attempting to delete a nonexistent service profile. + + :returns: ``None`` + """ + self._delete(_service_profile.ServiceProfile, service_profile, + ignore_missing=ignore_missing) + + def find_service_profile(self, name_or_id, ignore_missing=True): + """Find a single network service flavor profile + + :param name_or_id: The name or ID of a service profile. + :param bool ignore_missing: When set to ``False`` + :class:`~openstack.exceptions.ResourceNotFound` will be + raised when the resource does not exist. + When set to ``True``, None will be returned when + attempting to find a nonexistent resource. + :returns: One :class:`~openstack.network.v2.service_profile + .ServiceProfile` or None + """ + return self._find(_service_profile.ServiceProfile, name_or_id, + ignore_missing=ignore_missing) + + def get_service_profile(self, service_profile): + """Get a single network service flavor profile + + :param service_profile: The value can be the ID of a service_profile or + a + :class:`~openstack.network.v2.service_profile + .ServiceProfile` instance. + + :returns: One :class:`~openstack.network.v2.service_profile + .ServiceProfile` + :raises: :class:`~openstack.exceptions.ResourceNotFound` + when no resource can be found. + """ + return self._get(_service_profile.ServiceProfile, service_profile) + + def service_profiles(self, **query): + """Return a generator of network service flavor profiles + + :param kwargs \*\*query: Optional query parameters to be sent to limit + the resources being returned. + + :returns: A generator of service profile objects + :rtype: :class:`~openstack.network.v2.service_profile.ServiceProfile` + """ + return self._list(_service_profile.ServiceProfile, paginated=True, + **query) + + def update_service_profile(self, service_profile, **attrs): + """Update a network flavor service profile + + :param service_profile: Either the id of a service profile or a + :class:`~openstack.network.v2.service_profile + .ServiceProfile` instance. + :attrs kwargs: The attributes to update on the service profile + represented by ``value``. + + :returns: The updated service profile + :rtype: :class:`~openstack.network.v2.service_profile.ServiceProfile` + """ + return self._update(_service_profile.ServiceProfile, service_profile, + **attrs) + def create_subnet(self, **attrs): """Create a new subnet from attributes diff --git a/openstack/network/v2/service_profile.py b/openstack/network/v2/service_profile.py new file mode 100644 index 00000000..7cf66ddd --- /dev/null +++ b/openstack/network/v2/service_profile.py @@ -0,0 +1,40 @@ +# Licensed under the Apache License, Version 2.0 (the "License"); you may +# not use this file except in compliance with the License. You may obtain +# a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT +# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the +# License for the specific language governing permissions and limitations +# under the License. + +from openstack.network import network_service +from openstack import resource + + +class ServiceProfile(resource.Resource): + resource_key = 'service_profile' + resources_key = 'service_profiles' + base_path = '/service_profiles' + service = network_service.NetworkService() + + # capabilities + allow_create = True + allow_retrieve = True + allow_update = True + allow_delete = True + allow_list = True + + # Properties + #: Description of the service flavor profile. + description = resource.prop('description') + #: Provider Driver for the service flavor profile + driver = resource.prop('driver') + #: Sets enabled flag + is_enabled = resource.prop('enabled', type=bool) + #: Metainformation of the service flavor profile + metainfo = resource.prop('metainfo') + #: The owner project ID + project_id = resource.prop('tenant_id') diff --git a/openstack/tests/functional/network/v2/test_service_profile.py b/openstack/tests/functional/network/v2/test_service_profile.py new file mode 100644 index 00000000..34fe31ac --- /dev/null +++ b/openstack/tests/functional/network/v2/test_service_profile.py @@ -0,0 +1,64 @@ +# Licensed under the Apache License, Version 2.0 (the "License"); you may +# not use this file except in compliance with the License. You may obtain +# a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT +# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the +# License for the specific language governing permissions and limitations +# under the License. + +from openstack.network.v2 import service_profile as _service_profile +from openstack.tests.functional import base + + +class TestServiceProfile(base.BaseFunctionalTest): + + SERVICE_PROFILE_DESCRIPTION = "DESCRIPTION" + UPDATE_DESCRIPTION = "UPDATED-DESCRIPTION" + METAINFO = "FlAVOR_PROFILE_METAINFO" + ID = None + + @classmethod + def setUpClass(cls): + super(TestServiceProfile, cls).setUpClass() + service_profiles = cls.conn.network.create_service_profile( + description=cls.SERVICE_PROFILE_DESCRIPTION, + metainfo=cls.METAINFO,) + assert isinstance(service_profiles, _service_profile.ServiceProfile) + cls.assertIs(cls.SERVICE_PROFILE_DESCRIPTION, + service_profiles.description) + cls.assertIs(cls.METAINFO, service_profiles.metainfo) + + cls.ID = service_profiles.id + + @classmethod + def tearDownClass(cls): + service_profiles = cls.conn.network.delete_service_profile( + cls.ID, + ignore_missing=True) + cls.assertIs(None, service_profiles) + + def test_find(self): + service_profiles = self.conn.network.find_service_profile( + self.ID) + self.assertEqual(self.METAINFO, + service_profiles.metainfo) + + def test_get(self): + service_profiles = self.conn.network.get_service_profile(self.ID) + self.assertEqual(self.METAINFO, service_profiles.metainfo) + self.assertEqual(self.SERVICE_PROFILE_DESCRIPTION, + service_profiles.description) + + def test_update(self): + service_profiles = self.conn.network.update_service_profile( + self.ID, + description=self.UPDATE_DESCRIPTION) + self.assertEqual(self.UPDATE_DESCRIPTION, service_profiles.description) + + def test_list(self): + metainfos = [f.metainfo for f in self.conn.network.service_profiles()] + self.assertIn(self.METAINFO, metainfos) diff --git a/openstack/tests/unit/network/v2/test_proxy.py b/openstack/tests/unit/network/v2/test_proxy.py index 6ed4d2c8..71412597 100644 --- a/openstack/tests/unit/network/v2/test_proxy.py +++ b/openstack/tests/unit/network/v2/test_proxy.py @@ -41,6 +41,7 @@ from openstack.network.v2 import router from openstack.network.v2 import security_group from openstack.network.v2 import security_group_rule from openstack.network.v2 import segment +from openstack.network.v2 import service_profile from openstack.network.v2 import service_provider from openstack.network.v2 import subnet from openstack.network.v2 import subnet_pool @@ -318,6 +319,30 @@ class TestNetworkProxy(test_proxy_base.TestProxyBase): self.verify_list(self.proxy.flavors, flavor.Flavor, paginated=True) + def test_service_profile_create_attrs(self): + self.verify_create(self.proxy.create_service_profile, + service_profile.ServiceProfile) + + def test_service_profile_delete(self): + self.verify_delete(self.proxy.delete_service_profile, + service_profile.ServiceProfile, True) + + def test_service_profile_find(self): + self.verify_find(self.proxy.find_service_profile, + service_profile.ServiceProfile) + + def test_service_profile_get(self): + self.verify_get(self.proxy.get_service_profile, + service_profile.ServiceProfile) + + def test_service_profiles(self): + self.verify_list(self.proxy.service_profiles, + service_profile.ServiceProfile, paginated=True) + + def test_service_profile_update(self): + self.verify_update(self.proxy.update_service_profile, + service_profile.ServiceProfile) + def test_network_ip_availability_find(self): self.verify_find(self.proxy.find_network_ip_availability, network_ip_availability.NetworkIPAvailability) diff --git a/openstack/tests/unit/network/v2/test_service_profile.py b/openstack/tests/unit/network/v2/test_service_profile.py new file mode 100644 index 00000000..2023c00b --- /dev/null +++ b/openstack/tests/unit/network/v2/test_service_profile.py @@ -0,0 +1,59 @@ +# Licensed under the Apache License, Version 2.0 (the "License"); you may +# not use this file except in compliance with the License. You may obtain +# a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT +# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the +# License for the specific language governing permissions and limitations +# under the License. + +import testtools + +from openstack.network.v2 import service_profile + +IDENTIFIER = 'IDENTIFIER' +EXAMPLE_WITH_OPTIONAL = { + 'description': 'test flavor profile', + 'driver': 'neutron_lbaas.drivers.octavia.driver.OctaviaDriver', + 'enabled': True, + 'metainfo': {'foo': 'bar'}, + 'tenant_id': '5', +} + +EXAMPLE = { + 'driver': 'neutron_lbaas.drivers.octavia.driver.OctaviaDriver', +} + + +class TestServiceProfile(testtools.TestCase): + def test_basic(self): + service_profiles = service_profile.ServiceProfile() + self.assertEqual('service_profile', service_profiles.resource_key) + self.assertEqual('service_profiles', service_profiles.resources_key) + self.assertEqual('/service_profiles', service_profiles.base_path) + self.assertTrue(service_profiles.allow_create) + self.assertTrue(service_profiles.allow_retrieve) + self.assertTrue(service_profiles.allow_update) + self.assertTrue(service_profiles.allow_delete) + self.assertTrue(service_profiles.allow_list) + + def test_make_it(self): + service_profiles = service_profile.ServiceProfile(EXAMPLE) + self.assertEqual(EXAMPLE['driver'], service_profiles.driver) + + def test_make_it_with_optional(self): + service_profiles = service_profile.ServiceProfile( + EXAMPLE_WITH_OPTIONAL) + self.assertEqual(EXAMPLE_WITH_OPTIONAL['description'], + service_profiles.description) + self.assertEqual(EXAMPLE_WITH_OPTIONAL['driver'], + service_profiles.driver) + self.assertEqual(EXAMPLE_WITH_OPTIONAL['enabled'], + service_profiles.is_enabled) + self.assertEqual(EXAMPLE_WITH_OPTIONAL['metainfo'], + service_profiles.metainfo) + self.assertEqual(EXAMPLE_WITH_OPTIONAL['tenant_id'], + service_profiles.tenant_id)