diff --git a/magnum/api/controllers/v1/cluster.py b/magnum/api/controllers/v1/cluster.py index eb7d5bc636..e5afe0d059 100755 --- a/magnum/api/controllers/v1/cluster.py +++ b/magnum/api/controllers/v1/cluster.py @@ -554,6 +554,11 @@ class ClustersController(base.Controller): :param cluster_ident: UUID of cluster or logical name of the cluster. """ context = pecan.request.context + if context.is_admin: + policy.enforce(context, 'cluster:delete_all_projects', + action='cluster:delete_all_projects') + context.all_tenants = True + cluster = api_utils.get_resource('Cluster', cluster_ident) policy.enforce(context, 'cluster:delete', cluster.as_dict(), action='cluster:delete') diff --git a/magnum/api/controllers/v1/cluster_template.py b/magnum/api/controllers/v1/cluster_template.py index d85c43d4bc..a1536101d8 100644 --- a/magnum/api/controllers/v1/cluster_template.py +++ b/magnum/api/controllers/v1/cluster_template.py @@ -464,6 +464,11 @@ class ClusterTemplatesController(base.Controller): ClusterTemplate. """ context = pecan.request.context + if context.is_admin: + policy.enforce(context, 'clustertemplate:delete_all_projects', + action='clustertemplate:delete_all_projects') + context.all_tenants = True + cluster_template = api_utils.get_resource('ClusterTemplate', cluster_template_ident) policy.enforce(context, 'clustertemplate:delete', diff --git a/magnum/common/policies/cluster.py b/magnum/common/policies/cluster.py index 70cd6cb3f6..a15425b1b6 100644 --- a/magnum/common/policies/cluster.py +++ b/magnum/common/policies/cluster.py @@ -40,6 +40,17 @@ rules = [ } ] ), + policy.DocumentedRuleDefault( + name=CLUSTER % 'delete_all_projects', + check_str=base.RULE_ADMIN_API, + description='Delete a cluster from any project.', + operations=[ + { + 'path': '/v1/clusters/{cluster_ident}', + 'method': 'DELETE' + } + ] + ), policy.DocumentedRuleDefault( name=CLUSTER % 'detail', check_str=base.RULE_DENY_CLUSTER_USER, diff --git a/magnum/common/policies/cluster_template.py b/magnum/common/policies/cluster_template.py index eec530f280..ac9844b269 100644 --- a/magnum/common/policies/cluster_template.py +++ b/magnum/common/policies/cluster_template.py @@ -40,6 +40,17 @@ rules = [ } ] ), + policy.DocumentedRuleDefault( + name=CLUSTER_TEMPLATE % 'delete_all_projects', + check_str=base.RULE_ADMIN_API, + description='Delete a cluster template from any project.', + operations=[ + { + 'path': '/v1/clustertemplate/{clustertemplate_ident}', + 'method': 'DELETE' + } + ] + ), policy.DocumentedRuleDefault( name=CLUSTER_TEMPLATE % 'detail_all_projects', check_str=base.RULE_ADMIN_API, diff --git a/magnum/tests/unit/api/controllers/v1/test_cluster.py b/magnum/tests/unit/api/controllers/v1/test_cluster.py index 391e74c038..c2f563c227 100644 --- a/magnum/tests/unit/api/controllers/v1/test_cluster.py +++ b/magnum/tests/unit/api/controllers/v1/test_cluster.py @@ -950,6 +950,16 @@ class TestDelete(api_base.FunctionalTest): self.assertEqual('application/json', response.content_type) self.assertTrue(response.json['errors']) + @mock.patch("magnum.common.policy.enforce") + @mock.patch("magnum.common.context.make_context") + def test_delete_cluster_as_admin(self, mock_context, mock_policy): + temp_uuid = uuidutils.generate_uuid() + obj_utils.create_test_cluster(self.context, uuid=temp_uuid) + self.context.is_admin = True + response = self.delete('/clusters/%s' % temp_uuid, + expect_errors=True) + self.assertEqual(204, response.status_int) + class TestClusterPolicyEnforcement(api_base.FunctionalTest): def setUp(self): diff --git a/magnum/tests/unit/api/controllers/v1/test_cluster_template.py b/magnum/tests/unit/api/controllers/v1/test_cluster_template.py index 5ef612ba9f..6e2b357207 100644 --- a/magnum/tests/unit/api/controllers/v1/test_cluster_template.py +++ b/magnum/tests/unit/api/controllers/v1/test_cluster_template.py @@ -1077,6 +1077,17 @@ class TestDelete(api_base.FunctionalTest): self.assertEqual('application/json', response.content_type) self.assertTrue(response.json['errors']) + @mock.patch("magnum.common.policy.enforce") + @mock.patch("magnum.common.context.make_context") + def test_delete_cluster_template_as_admin(self, mock_context, mock_policy): + temp_uuid = uuidutils.generate_uuid() + obj_utils.create_test_cluster_template(self.context, uuid=temp_uuid, + project_id=temp_uuid) + self.context.is_admin = True + response = self.delete('/clustertemplates/%s' % temp_uuid, + expect_errors=True) + self.assertEqual(204, response.status_int) + class TestClusterTemplatePolicyEnforcement(api_base.FunctionalTest):