From a7d4a9bd4c620dae127b53fed8bdaf0ea3055635 Mon Sep 17 00:00:00 2001 From: wangxiyuan Date: Thu, 5 Jul 2018 09:40:50 +0800 Subject: [PATCH] Update project depth check when a hierarchical limit enforcement model is deployed by keystone, the project hierarchical depth should not break the limit model as well. This patch updated the project depth check function to fix the problem. bp: strict-two-level-model Change-Id: I695fedcf83bdca2946a2c5d876052c02b0f63810 --- keystone/resource/core.py | 9 ++++++ keystone/tests/unit/test_v3_resource.py | 29 +++++++++++++++++++ .../notes/bp-strict-two-level-model.yaml | 3 ++ 3 files changed, 41 insertions(+) diff --git a/keystone/resource/core.py b/keystone/resource/core.py index 76d8fb728c..a135f1fcce 100644 --- a/keystone/resource/core.py +++ b/keystone/resource/core.py @@ -76,6 +76,15 @@ class Manager(manager.Manager): # pushing any existing hierarchies over the limit, we add one to the # maximum depth allowed, as specified in the configuration file. max_depth = CONF.max_project_tree_depth + 1 + + # NOTE(wxy): If the hierarchical limit enforcement model is used, the + # project depth should be not greater than the model's limit as well. + # + # TODO(wxy): Deprecate and remove CONF.max_project_tree_depth, let the + # depth check only based on the limit enforcement model. + limit_model = PROVIDERS.unified_limit_api.enforcement_model + if limit_model.MAX_PROJECT_TREE_DEPTH is not None: + max_depth = min(max_depth, limit_model.MAX_PROJECT_TREE_DEPTH + 1) if self._get_hierarchy_depth(parents_list) > max_depth: raise exception.ForbiddenNotSecurity( _('Max hierarchy depth reached for %s branch.') % project_id) diff --git a/keystone/tests/unit/test_v3_resource.py b/keystone/tests/unit/test_v3_resource.py index b94e28822e..929f78b979 100644 --- a/keystone/tests/unit/test_v3_resource.py +++ b/keystone/tests/unit/test_v3_resource.py @@ -1798,3 +1798,32 @@ class ResourceTestCase(test_v3.RestfulTestCase, resp = self.get('/users/%(user)s/projects' % {'user': user['id']}) self.assertValidProjectListResponse(resp) self.assertEqual(project['id'], resp.result['projects'][0]['id']) + + +class StrictTwoLevelLimitsResourceTestCase(ResourceTestCase): + def setUp(self): + super(StrictTwoLevelLimitsResourceTestCase, self).setUp() + + def config_overrides(self): + super(StrictTwoLevelLimitsResourceTestCase, self).config_overrides() + self.config_fixture.config(group='unified_limit', + enforcement_model='strict_two_level') + + def _create_projects_hierarchy(self, hierarchy_size=1): + if hierarchy_size > 1: + self.skip_test_overrides( + "Strict two level limit enforcement model doesn't allow the" + "project tree depth > 2") + return super(StrictTwoLevelLimitsResourceTestCase, + self)._create_projects_hierarchy(hierarchy_size) + + def test_create_hierarchical_project(self): + projects = self._create_projects_hierarchy() + + # create grandchild project will fail. + new_ref = unit.new_project_ref( + domain_id=self.domain_id, + parent_id=projects[1]['project']['id']) + self.post('/projects', + body={'project': new_ref}, + expected_status=http_client.FORBIDDEN) diff --git a/releasenotes/notes/bp-strict-two-level-model.yaml b/releasenotes/notes/bp-strict-two-level-model.yaml index 8f15057be8..1fc57f0651 100644 --- a/releasenotes/notes/bp-strict-two-level-model.yaml +++ b/releasenotes/notes/bp-strict-two-level-model.yaml @@ -14,6 +14,9 @@ features: Please ensure that the previous project and limit structure deployment in your Keystone won't break this model before starting to use it. + If a newly created project results in a project tree depth greater than 2, a + `403 Forbidden` error will be raised. + - > [`blueprint strict-two-level-model `_] The `project_id` filter is added for listing limits. This filter is used