From 5e3e66f6a833a73b399c918f24f563afb939aa9e Mon Sep 17 00:00:00 2001 From: Sumit Naiksatam Date: Mon, 20 Mar 2017 16:47:40 -0700 Subject: [PATCH] Add Application Policy Group resource Change-Id: I0eb9f444ffb8325af0dfee48e1a07eda41f53161 Implements: blueprint application-group --- .../heat/engine/resources/grouppolicy.py | 88 +++++++- gbpautomation/heat/tests/test_grouppolicy.py | 202 ++++++++++++++++++ 2 files changed, 284 insertions(+), 6 deletions(-) diff --git a/gbpautomation/heat/engine/resources/grouppolicy.py b/gbpautomation/heat/engine/resources/grouppolicy.py index 44a936b..238902a 100644 --- a/gbpautomation/heat/engine/resources/grouppolicy.py +++ b/gbpautomation/heat/engine/resources/grouppolicy.py @@ -21,6 +21,76 @@ from heat.engine import properties from neutronclient.common.exceptions import NeutronClientException +class ApplicationPolicyGroup(gbpresource.GBPResource): + + PROPERTIES = ( + TENANT_ID, NAME, DESCRIPTION, SHARED + ) = ( + 'tenant_id', 'name', 'description', 'shared' + ) + + properties_schema = { + TENANT_ID: properties.Schema( + properties.Schema.STRING, + _('Tenant id of the Application Policy Group.') + ), + NAME: properties.Schema( + properties.Schema.STRING, + _('Name of the Application Policy Group.'), + update_allowed=True + ), + DESCRIPTION: properties.Schema( + properties.Schema.STRING, + _('Description of the Application Policy Group.'), + update_allowed=True + ), + SHARED: properties.Schema( + properties.Schema.BOOLEAN, + _('Shared.'), + update_allowed=True, required=True + ) + } + + def _show_resource(self): + client = self.grouppolicy() + application_policy_group_id = self.resource_id + return client.show_application_policy_group( + application_policy_group_id)['application_policy_group'] + + def handle_create(self): + client = self.grouppolicy() + + props = {} + for key in self.properties: + if self.properties.get(key) is not None: + props[key] = self.properties.get(key) + + application_policy_group = ( + client.create_application_policy_group( + {'application_policy_group': + props})['application_policy_group']) + + self.resource_id_set(application_policy_group['id']) + + def handle_delete(self): + + client = self.grouppolicy() + application_policy_group_id = self.resource_id + + try: + client.delete_application_policy_group( + application_policy_group_id) + except NeutronClientException as ex: + self.client_plugin().ignore_not_found(ex) + else: + return self._delete_task() + + def handle_update(self, json_snippet, tmpl_diff, prop_diff): + if prop_diff: + self.grouppolicy().update_application_policy_group( + self.resource_id, {'application_policy_group': prop_diff}) + + class PolicyTarget(gbpresource.GBPResource): PROPERTIES = ( @@ -148,13 +218,14 @@ class PolicyTarget(gbpresource.GBPResource): class PolicyTargetGroup(gbpresource.GBPResource): PROPERTIES = ( - TENANT_ID, NAME, DESCRIPTION, L2_POLICY_ID, PROVIDED_POLICY_RULE_SETS, - CONSUMED_POLICY_RULE_SETS, NETWORK_SERVICE_POLICY_ID, SHARED, - INTRA_PTG_ALLOW + TENANT_ID, NAME, DESCRIPTION, APPLICATION_POLICY_GROUP_ID, + L2_POLICY_ID, PROVIDED_POLICY_RULE_SETS, CONSUMED_POLICY_RULE_SETS, + NETWORK_SERVICE_POLICY_ID, SHARED, INTRA_PTG_ALLOW ) = ( - 'tenant_id', 'name', 'description', 'l2_policy_id', - 'provided_policy_rule_sets', 'consumed_policy_rule_sets', - 'network_service_policy_id', 'shared', 'intra_ptg_allow' + 'tenant_id', 'name', 'description', 'application_policy_group_id', + 'l2_policy_id', 'provided_policy_rule_sets', + 'consumed_policy_rule_sets', 'network_service_policy_id', 'shared', + 'intra_ptg_allow' ) properties_schema = { @@ -172,6 +243,11 @@ class PolicyTargetGroup(gbpresource.GBPResource): _('Description of the policy target group.'), update_allowed=True ), + APPLICATION_POLICY_GROUP_ID: properties.Schema( + properties.Schema.STRING, + _('Application Policy Group id of the policy target group.'), + update_allowed=True + ), L2_POLICY_ID: properties.Schema( properties.Schema.STRING, _('L2 policy id of the policy target group.'), diff --git a/gbpautomation/heat/tests/test_grouppolicy.py b/gbpautomation/heat/tests/test_grouppolicy.py index 1f7829c..648db77 100644 --- a/gbpautomation/heat/tests/test_grouppolicy.py +++ b/gbpautomation/heat/tests/test_grouppolicy.py @@ -23,6 +23,25 @@ from heat.engine import scheduler from heat.tests import utils +application_policy_group_template = ''' +{ + "AWSTemplateFormatVersion" : "2010-09-09", + "Description" : "Template to test GBP application policy group", + "Parameters" : {}, + "Resources" : { + "application_policy_group": { + "Type": "OS::GroupBasedPolicy::ApplicationPolicyGroup", + "Properties": { + "name": "test-application-policy-group", + "description": "test APG resource", + "shared": True + } + } + } +} +''' + + policy_target_template = ''' { "AWSTemplateFormatVersion" : "2010-09-09", @@ -97,6 +116,39 @@ policy_target_group_template = ''' } ''' +policy_target_group_with_apg_template = ''' +{ + "AWSTemplateFormatVersion" : "2010-09-09", + "Description" : "Template to test neutron policy target group resource", + "Parameters" : {}, + "Resources" : { + "policy_target_group": { + "Type": "OS::GroupBasedPolicy::PolicyTargetGroup", + "Properties": { + "name": "test-policy-target-group", + "description": "test policy target group resource", + "application_policy_group_id": "apg-id", + "l2_policy_id": "l2-policy-id", + "provided_policy_rule_sets": [ + {"policy_rule_set_id": "policy_rule_set1", + "policy_rule_set_scope": "scope1"}, + {"policy_rule_set_id": "policy_rule_set2", + "policy_rule_set_scope": "scope2"} + ], + "consumed_policy_rule_sets": [ + {"policy_rule_set_id": "policy_rule_set3", + "policy_rule_set_scope": "scope3"}, + {"policy_rule_set_id": "policy_rule_set4", + "policy_rule_set_scope": "scope4"} + ], + "shared": True, + "intra_ptg_allow": False + } + } + } +} +''' + l2_policy_template = ''' { "AWSTemplateFormatVersion" : "2010-09-09", @@ -329,6 +381,122 @@ nat_pool_template = ''' ''' +class ApplicationPolicyGroupTest(HeatTestCase): + + def setUp(self): + super(ApplicationPolicyGroupTest, self).setUp() + self.m.StubOutWithMock(gbpclient.Client, + 'create_application_policy_group') + self.m.StubOutWithMock(gbpclient.Client, + 'delete_application_policy_group') + self.m.StubOutWithMock(gbpclient.Client, + 'show_application_policy_group') + self.m.StubOutWithMock(gbpclient.Client, + 'update_application_policy_group') + self.stub_keystoneclient() + + def create_application_policy_group(self): + gbpclient.Client.create_application_policy_group({ + 'application_policy_group': { + "name": "test-application-policy-group", + "description": "test APG resource", + "shared": True + } + }).AndReturn({'application_policy_group': {'id': '5678'}}) + + snippet = template_format.parse(application_policy_group_template) + self.stack = utils.parse_stack(snippet) + resource_defns = self.stack.t.resource_definitions(self.stack) + return grouppolicy.ApplicationPolicyGroup( + 'application_policy_group', + resource_defns['application_policy_group'], self.stack) + + def test_create(self): + rsrc = self.create_application_policy_group() + self.m.ReplayAll() + scheduler.TaskRunner(rsrc.create)() + self.assertEqual((rsrc.CREATE, rsrc.COMPLETE), rsrc.state) + self.m.VerifyAll() + + def test_create_failed(self): + gbpclient.Client.create_application_policy_group({ + 'application_policy_group': { + "name": "test-application-policy-group", + "description": "test APG resource", + "shared": True + } + }).AndRaise(grouppolicy.NeutronClientException()) + self.m.ReplayAll() + + snippet = template_format.parse(application_policy_group_template) + self.stack = utils.parse_stack(snippet) + resource_defns = self.stack.t.resource_definitions(self.stack) + rsrc = grouppolicy.ApplicationPolicyGroup( + 'application_policy_group', + resource_defns['application_policy_group'], self.stack) + + error = self.assertRaises(exception.ResourceFailure, + scheduler.TaskRunner(rsrc.create)) + self.assertEqual( + 'NeutronClientException: resources.application_policy_group: ' + 'An unknown exception occurred.', + six.text_type(error)) + self.assertEqual((rsrc.CREATE, rsrc.FAILED), rsrc.state) + self.m.VerifyAll() + + def test_delete(self): + gbpclient.Client.delete_application_policy_group('5678') + gbpclient.Client.show_application_policy_group('5678').AndRaise( + grouppolicy.NeutronClientException(status_code=404)) + + rsrc = self.create_application_policy_group() + self.m.ReplayAll() + scheduler.TaskRunner(rsrc.create)() + scheduler.TaskRunner(rsrc.delete)() + self.assertEqual((rsrc.DELETE, rsrc.COMPLETE), rsrc.state) + self.m.VerifyAll() + + def test_delete_already_gone(self): + gbpclient.Client.delete_application_policy_group('5678').AndRaise( + grouppolicy.NeutronClientException(status_code=404)) + + rsrc = self.create_application_policy_group() + self.m.ReplayAll() + scheduler.TaskRunner(rsrc.create)() + scheduler.TaskRunner(rsrc.delete)() + self.assertEqual((rsrc.DELETE, rsrc.COMPLETE), rsrc.state) + self.m.VerifyAll() + + def test_delete_failed(self): + gbpclient.Client.delete_application_policy_group('5678').AndRaise( + grouppolicy.NeutronClientException(status_code=400)) + + rsrc = self.create_application_policy_group() + self.m.ReplayAll() + scheduler.TaskRunner(rsrc.create)() + error = self.assertRaises(exception.ResourceFailure, + scheduler.TaskRunner(rsrc.delete)) + self.assertEqual( + 'NeutronClientException: resources.application_policy_group: ' + 'An unknown exception occurred.', + six.text_type(error)) + self.assertEqual((rsrc.DELETE, rsrc.FAILED), rsrc.state) + self.m.VerifyAll() + + def test_update(self): + rsrc = self.create_application_policy_group() + gbpclient.Client.update_application_policy_group( + '5678', {'application_policy_group': {'name': 'new name'}}) + self.m.ReplayAll() + scheduler.TaskRunner(rsrc.create)() + + update_template = copy.deepcopy(rsrc.t) + update_template['Properties']['name'] = 'new name' + scheduler.TaskRunner(rsrc.update, update_template)() + + self.m.VerifyAll() + + class PolicyTargetTest(HeatTestCase): def setUp(self): @@ -529,6 +697,33 @@ class PolicyTargetGroupTest(HeatTestCase): 'policy_target_group', resource_defns['policy_target_group'], self.stack) + def create_policy_target_group_with_apg(self): + gbpclient.Client.create_policy_target_group({ + "policy_target_group": { + "name": "test-policy-target-group", + "description": "test policy target group resource", + "application_policy_group_id": "apg-id", + "l2_policy_id": "l2-policy-id", + "provided_policy_rule_sets": { + "policy_rule_set1": "scope1", + "policy_rule_set2": "scope2" + }, + "consumed_policy_rule_sets": { + "policy_rule_set3": "scope3", + "policy_rule_set4": "scope4" + }, + "shared": True, + "intra_ptg_allow": False + } + }).AndReturn({'policy_target_group': {'id': '5678'}}) + + snippet = template_format.parse(policy_target_group_with_apg_template) + self.stack = utils.parse_stack(snippet) + resource_defns = self.stack.t.resource_definitions(self.stack) + return grouppolicy.PolicyTargetGroup( + 'policy_target_group', resource_defns['policy_target_group'], + self.stack) + def test_create(self): rsrc = self.create_policy_target_group() self.m.ReplayAll() @@ -536,6 +731,13 @@ class PolicyTargetGroupTest(HeatTestCase): self.assertEqual((rsrc.CREATE, rsrc.COMPLETE), rsrc.state) self.m.VerifyAll() + def test_create_with_apg(self): + rsrc = self.create_policy_target_group_with_apg() + self.m.ReplayAll() + scheduler.TaskRunner(rsrc.create)() + self.assertEqual((rsrc.CREATE, rsrc.COMPLETE), rsrc.state) + self.m.VerifyAll() + def test_create_failed(self): gbpclient.Client.create_policy_target_group({ "policy_target_group": {