Merge "Enable new defaults and scope checks by default"
This commit is contained in:
+34
@@ -665,6 +665,36 @@
|
||||
parent: tempest-integrated-compute
|
||||
nodeset: openstack-single-node-focal
|
||||
|
||||
# TODO(gmann): Remove this jobs once all the required services for intergrate
|
||||
# compute gate (Cinder, Glance, Neutron) by default enable scope and new
|
||||
# defaults which means all the nova jobs will be tested with new RBAC in
|
||||
# integrated way and we do not need this separate job.
|
||||
- job:
|
||||
name: tempest-integrated-compute-enforce-scope-new-defaults
|
||||
parent: tempest-integrated-compute
|
||||
description: |
|
||||
This job runs the Tempest tests with scope and new defaults enabled
|
||||
for Nova, Neutron, Glance, and Cinder services.
|
||||
# TODO (gmann): There were few fixes in neutron and neutron-lib for the
|
||||
# RBAC but they are not yet released so we need to add both projcts as
|
||||
# the required-projects. Those can be removed once new version of neutron
|
||||
# and neutron-lib is released.
|
||||
required-projects:
|
||||
- openstack/neutron
|
||||
- openstack/neutron-lib
|
||||
vars:
|
||||
devstack_localrc:
|
||||
# Enabeling the scope and new defaults for services implemented it.
|
||||
# NOTE (gmann): We need to keep keystone scope check disable as
|
||||
# services (except ironic) does not support the system scope and
|
||||
# they need keystone to continue working with project scope. Until
|
||||
# Keystone policies are changed to work for project scoped also, we
|
||||
# need to keep scope check disable for keystone.
|
||||
NOVA_ENFORCE_SCOPE: true
|
||||
CINDER_ENFORCE_SCOPE: true
|
||||
GLANCE_ENFORCE_SCOPE: true
|
||||
NEUTRON_ENFORCE_SCOPE: true
|
||||
|
||||
- project:
|
||||
# Please try to keep the list of job names sorted alphabetically.
|
||||
templates:
|
||||
@@ -723,6 +753,8 @@
|
||||
- ^tox.ini$
|
||||
- tempest-integrated-compute-ubuntu-focal:
|
||||
irrelevant-files: *policies-irrelevant-files
|
||||
- tempest-integrated-compute-enforce-scope-new-defaults:
|
||||
irrelevant-files: *policies-irrelevant-files
|
||||
- grenade-skip-level:
|
||||
irrelevant-files: *policies-irrelevant-files
|
||||
- nova-grenade-multinode:
|
||||
@@ -758,6 +790,8 @@
|
||||
irrelevant-files: *policies-irrelevant-files
|
||||
- tempest-integrated-compute-ubuntu-focal:
|
||||
irrelevant-files: *policies-irrelevant-files
|
||||
- tempest-integrated-compute-enforce-scope-new-defaults:
|
||||
irrelevant-files: *policies-irrelevant-files
|
||||
- nova-grenade-multinode:
|
||||
irrelevant-files: *policies-irrelevant-files
|
||||
- tempest-ipv6-only:
|
||||
|
||||
+8
-4
@@ -41,11 +41,15 @@ USER_BASED_RESOURCES = ['os-keypairs']
|
||||
saved_file_rules = []
|
||||
KEY_EXPR = re.compile(r'%\((\w+)\)s')
|
||||
|
||||
# TODO(gmann): Remove setting the default value of config policy_file
|
||||
# once oslo_policy change the default value to 'policy.yaml'.
|
||||
# https://github.com/openstack/oslo.policy/blob/a626ad12fe5a3abd49d70e3e5b95589d279ab578/oslo_policy/opts.py#L49
|
||||
# TODO(gmann): Remove overriding the default value of config options
|
||||
# 'policy_file', 'enforce_scope', and 'enforce_new_defaults' once
|
||||
# oslo_policy change their default value to what is overridden here.
|
||||
DEFAULT_POLICY_FILE = 'policy.yaml'
|
||||
opts.set_defaults(cfg.CONF, DEFAULT_POLICY_FILE)
|
||||
opts.set_defaults(
|
||||
cfg.CONF,
|
||||
DEFAULT_POLICY_FILE,
|
||||
enforce_scope=True,
|
||||
enforce_new_defaults=True)
|
||||
|
||||
|
||||
def reset():
|
||||
|
||||
@@ -87,7 +87,8 @@ class ServerGroupTestV21(test.NoDBTestCase):
|
||||
def setUp(self):
|
||||
super(ServerGroupTestV21, self).setUp()
|
||||
self._setup_controller()
|
||||
self.req = fakes.HTTPRequest.blank('')
|
||||
self.member_req = fakes.HTTPRequest.member_req('')
|
||||
self.reader_req = fakes.HTTPRequest.reader_req('')
|
||||
self.admin_req = fakes.HTTPRequest.blank('', use_admin_context=True)
|
||||
self.foo_req = fakes.HTTPRequest.blank('', project_id='foo')
|
||||
self.policy = self.useFixture(fixtures.RealPolicyFixture())
|
||||
@@ -114,20 +115,20 @@ class ServerGroupTestV21(test.NoDBTestCase):
|
||||
def test_create_server_group_with_no_policies(self):
|
||||
sgroup = server_group_template()
|
||||
self.assertRaises(self.validation_error, self.controller.create,
|
||||
self.req, body={'server_group': sgroup})
|
||||
self.member_req, body={'server_group': sgroup})
|
||||
|
||||
def _create_server_group_normal(self, policies=None, policy=None,
|
||||
rules=None):
|
||||
sgroup = server_group_template()
|
||||
sgroup['policies'] = policies
|
||||
res_dict = self.controller.create(self.req,
|
||||
res_dict = self.controller.create(self.member_req,
|
||||
body={'server_group': sgroup})
|
||||
self.assertEqual(res_dict['server_group']['name'], 'test')
|
||||
self.assertTrue(uuidutils.is_uuid_like(res_dict['server_group']['id']))
|
||||
self.assertEqual(res_dict['server_group']['policies'], policies)
|
||||
|
||||
def test_create_server_group_with_new_policy_before_264(self):
|
||||
req = fakes.HTTPRequest.blank('', version='2.63')
|
||||
req = fakes.HTTPRequest.member_req('', version='2.63')
|
||||
policy = 'anti-affinity'
|
||||
rules = {'max_server_per_host': 3}
|
||||
# 'policy' isn't an acceptable request key before 2.64
|
||||
@@ -162,7 +163,7 @@ class ServerGroupTestV21(test.NoDBTestCase):
|
||||
self.controller.create(self.admin_req, body={'server_group': sgroup})
|
||||
|
||||
# test as non-admin
|
||||
self.controller.create(self.req, body={'server_group': sgroup})
|
||||
self.controller.create(self.member_req, body={'server_group': sgroup})
|
||||
|
||||
def _create_instance(self, ctx, cell):
|
||||
with context.target_cell(ctx, cell) as cctx:
|
||||
@@ -289,7 +290,7 @@ class ServerGroupTestV21(test.NoDBTestCase):
|
||||
path = path or '/os-server-groups?all_projects=True'
|
||||
if limited:
|
||||
path += limited
|
||||
req = fakes.HTTPRequest.blank(path, version=api_version)
|
||||
reader_req = fakes.HTTPRequest.reader_req(path, version=api_version)
|
||||
admin_req = fakes.HTTPRequest.blank(path, use_admin_context=True,
|
||||
version=api_version)
|
||||
|
||||
@@ -298,7 +299,7 @@ class ServerGroupTestV21(test.NoDBTestCase):
|
||||
self.assertEqual(all, res_dict)
|
||||
|
||||
# test as non-admin
|
||||
res_dict = self.controller.index(req)
|
||||
res_dict = self.controller.index(reader_req)
|
||||
self.assertEqual(tenant_specific, res_dict)
|
||||
|
||||
@mock.patch('nova.objects.InstanceGroupList.get_by_project_id')
|
||||
@@ -347,25 +348,27 @@ class ServerGroupTestV21(test.NoDBTestCase):
|
||||
return_get_by_project = return_server_groups()
|
||||
mock_get_by_project.return_value = return_get_by_project
|
||||
path = '/os-server-groups'
|
||||
req = fakes.HTTPRequest.blank(path, version=api_version)
|
||||
req = fakes.HTTPRequest.reader_req(path, version=api_version)
|
||||
res_dict = self.controller.index(req)
|
||||
self.assertEqual(expected, res_dict)
|
||||
|
||||
def test_display_members(self):
|
||||
ctx = context.RequestContext('fake_user', fakes.FAKE_PROJECT_ID)
|
||||
(ig_uuid, instances, members) = self._create_groups_and_instances(ctx)
|
||||
res_dict = self.controller.show(self.req, ig_uuid)
|
||||
res_dict = self.controller.show(self.reader_req, ig_uuid)
|
||||
result_members = res_dict['server_group']['members']
|
||||
self.assertEqual(3, len(result_members))
|
||||
for member in members:
|
||||
self.assertIn(member, result_members)
|
||||
|
||||
def test_display_members_with_nonexistent_group(self):
|
||||
self.assertRaises(webob.exc.HTTPNotFound,
|
||||
self.controller.show, self.req, uuidsentinel.group)
|
||||
self.assertRaises(
|
||||
webob.exc.HTTPNotFound,
|
||||
self.controller.show, self.reader_req, uuidsentinel.group)
|
||||
|
||||
def test_display_active_members_only(self):
|
||||
ctx = context.RequestContext('fake_user', fakes.FAKE_PROJECT_ID)
|
||||
ctx = context.RequestContext('fake_user', fakes.FAKE_PROJECT_ID,
|
||||
roles=['member', 'reader'])
|
||||
(ig_uuid, instances, members) = self._create_groups_and_instances(ctx)
|
||||
|
||||
# delete an instance
|
||||
@@ -379,7 +382,7 @@ class ServerGroupTestV21(test.NoDBTestCase):
|
||||
self.assertRaises(exception.InstanceNotFound,
|
||||
objects.Instance.get_by_uuid,
|
||||
ctx, instances[1].uuid)
|
||||
res_dict = self.controller.show(self.req, ig_uuid)
|
||||
res_dict = self.controller.show(self.reader_req, ig_uuid)
|
||||
result_members = res_dict['server_group']['members']
|
||||
# check that only the active instance is displayed
|
||||
self.assertEqual(2, len(result_members))
|
||||
@@ -393,7 +396,7 @@ class ServerGroupTestV21(test.NoDBTestCase):
|
||||
self.controller.show(self.admin_req, ig_uuid)
|
||||
|
||||
# test as non-admin, same project
|
||||
self.controller.show(self.req, ig_uuid)
|
||||
self.controller.show(self.reader_req, ig_uuid)
|
||||
|
||||
# test as non-admin, different project
|
||||
self.assertRaises(webob.exc.HTTPNotFound,
|
||||
@@ -406,7 +409,7 @@ class ServerGroupTestV21(test.NoDBTestCase):
|
||||
|
||||
sgroup = server_group_template(name='good* $%name',
|
||||
policies=['affinity'])
|
||||
res_dict = self.controller.create(self.req,
|
||||
res_dict = self.controller.create(self.member_req,
|
||||
body={'server_group': sgroup})
|
||||
self.assertEqual(res_dict['server_group']['name'], 'good* $%name')
|
||||
|
||||
@@ -414,99 +417,99 @@ class ServerGroupTestV21(test.NoDBTestCase):
|
||||
# blank name
|
||||
sgroup = server_group_template(name='', policies=['test_policy'])
|
||||
self.assertRaises(self.validation_error, self.controller.create,
|
||||
self.req, body={'server_group': sgroup})
|
||||
self.member_req, body={'server_group': sgroup})
|
||||
|
||||
# name with length 256
|
||||
sgroup = server_group_template(name='1234567890' * 26,
|
||||
policies=['test_policy'])
|
||||
self.assertRaises(self.validation_error, self.controller.create,
|
||||
self.req, body={'server_group': sgroup})
|
||||
self.member_req, body={'server_group': sgroup})
|
||||
|
||||
# non-string name
|
||||
sgroup = server_group_template(name=12, policies=['test_policy'])
|
||||
self.assertRaises(self.validation_error, self.controller.create,
|
||||
self.req, body={'server_group': sgroup})
|
||||
self.member_req, body={'server_group': sgroup})
|
||||
|
||||
# name with leading spaces
|
||||
sgroup = server_group_template(name=' leading spaces',
|
||||
policies=['test_policy'])
|
||||
self.assertRaises(self.validation_error, self.controller.create,
|
||||
self.req, body={'server_group': sgroup})
|
||||
self.member_req, body={'server_group': sgroup})
|
||||
|
||||
# name with trailing spaces
|
||||
sgroup = server_group_template(name='trailing space ',
|
||||
policies=['test_policy'])
|
||||
self.assertRaises(self.validation_error, self.controller.create,
|
||||
self.req, body={'server_group': sgroup})
|
||||
self.member_req, body={'server_group': sgroup})
|
||||
|
||||
# name with all spaces
|
||||
sgroup = server_group_template(name=' ',
|
||||
policies=['test_policy'])
|
||||
self.assertRaises(self.validation_error, self.controller.create,
|
||||
self.req, body={'server_group': sgroup})
|
||||
self.member_req, body={'server_group': sgroup})
|
||||
|
||||
# name with unprintable character
|
||||
sgroup = server_group_template(name='bad\x00name',
|
||||
policies=['test_policy'])
|
||||
self.assertRaises(self.validation_error, self.controller.create,
|
||||
self.req, body={'server_group': sgroup})
|
||||
self.member_req, body={'server_group': sgroup})
|
||||
|
||||
# name with out of range char U0001F4A9
|
||||
sgroup = server_group_template(name=u"\U0001F4A9",
|
||||
policies=['affinity'])
|
||||
self.assertRaises(self.validation_error, self.controller.create,
|
||||
self.req, body={'server_group': sgroup})
|
||||
self.member_req, body={'server_group': sgroup})
|
||||
|
||||
def test_create_server_group_with_illegal_policies(self):
|
||||
# blank policy
|
||||
sgroup = server_group_template(name='fake-name', policies='')
|
||||
self.assertRaises(self.validation_error, self.controller.create,
|
||||
self.req, body={'server_group': sgroup})
|
||||
self.member_req, body={'server_group': sgroup})
|
||||
|
||||
# policy as integer
|
||||
sgroup = server_group_template(name='fake-name', policies=7)
|
||||
self.assertRaises(self.validation_error, self.controller.create,
|
||||
self.req, body={'server_group': sgroup})
|
||||
self.member_req, body={'server_group': sgroup})
|
||||
|
||||
# policy as string
|
||||
sgroup = server_group_template(name='fake-name', policies='invalid')
|
||||
self.assertRaises(self.validation_error, self.controller.create,
|
||||
self.req, body={'server_group': sgroup})
|
||||
self.member_req, body={'server_group': sgroup})
|
||||
|
||||
# policy as None
|
||||
sgroup = server_group_template(name='fake-name', policies=None)
|
||||
self.assertRaises(self.validation_error, self.controller.create,
|
||||
self.req, body={'server_group': sgroup})
|
||||
self.member_req, body={'server_group': sgroup})
|
||||
|
||||
def test_create_server_group_conflicting_policies(self):
|
||||
sgroup = server_group_template()
|
||||
policies = ['anti-affinity', 'affinity']
|
||||
sgroup['policies'] = policies
|
||||
self.assertRaises(self.validation_error, self.controller.create,
|
||||
self.req, body={'server_group': sgroup})
|
||||
self.member_req, body={'server_group': sgroup})
|
||||
|
||||
def test_create_server_group_with_duplicate_policies(self):
|
||||
sgroup = server_group_template()
|
||||
policies = ['affinity', 'affinity']
|
||||
sgroup['policies'] = policies
|
||||
self.assertRaises(self.validation_error, self.controller.create,
|
||||
self.req, body={'server_group': sgroup})
|
||||
self.member_req, body={'server_group': sgroup})
|
||||
|
||||
def test_create_server_group_not_supported(self):
|
||||
sgroup = server_group_template()
|
||||
policies = ['storage-affinity', 'anti-affinity', 'rack-affinity']
|
||||
sgroup['policies'] = policies
|
||||
self.assertRaises(self.validation_error, self.controller.create,
|
||||
self.req, body={'server_group': sgroup})
|
||||
self.member_req, body={'server_group': sgroup})
|
||||
|
||||
def test_create_server_group_with_no_body(self):
|
||||
self.assertRaises(self.validation_error,
|
||||
self.controller.create, self.req, body=None)
|
||||
self.controller.create, self.member_req, body=None)
|
||||
|
||||
def test_create_server_group_with_no_server_group(self):
|
||||
body = {'no-instanceGroup': None}
|
||||
self.assertRaises(self.validation_error,
|
||||
self.controller.create, self.req, body=body)
|
||||
self.controller.create, self.member_req, body=body)
|
||||
|
||||
def test_list_server_group_by_tenant(self):
|
||||
self._test_list_server_group_by_tenant(
|
||||
@@ -528,7 +531,7 @@ class ServerGroupTestV21(test.NoDBTestCase):
|
||||
self.controller.index(self.admin_req)
|
||||
|
||||
# test as non-admin
|
||||
self.controller.index(self.req)
|
||||
self.controller.index(self.reader_req)
|
||||
|
||||
def test_list_server_group_multiple_param(self):
|
||||
self._test_list_server_group(api_version=self.wsgi_api_version,
|
||||
@@ -598,7 +601,7 @@ class ServerGroupTestV21(test.NoDBTestCase):
|
||||
self.stub_out('nova.objects.InstanceGroup.get_by_uuid',
|
||||
return_server_group)
|
||||
|
||||
resp = self.controller.delete(self.req, uuidsentinel.sg1_id)
|
||||
resp = self.controller.delete(self.member_req, uuidsentinel.sg1_id)
|
||||
mock_destroy.assert_called_once_with()
|
||||
|
||||
# NOTE: on v2.1, http status code is set as wsgi_code of API
|
||||
@@ -611,7 +614,7 @@ class ServerGroupTestV21(test.NoDBTestCase):
|
||||
|
||||
def test_delete_non_existing_server_group(self):
|
||||
self.assertRaises(webob.exc.HTTPNotFound, self.controller.delete,
|
||||
self.req, 'invalid')
|
||||
self.member_req, 'invalid')
|
||||
|
||||
def test_delete_server_group_rbac_default(self):
|
||||
ctx = context.RequestContext('fake_user', fakes.FAKE_PROJECT_ID)
|
||||
@@ -622,7 +625,7 @@ class ServerGroupTestV21(test.NoDBTestCase):
|
||||
|
||||
# test as non-admin
|
||||
ig_uuid = self._create_groups_and_instances(ctx)[0]
|
||||
self.controller.delete(self.req, ig_uuid)
|
||||
self.controller.delete(self.member_req, ig_uuid)
|
||||
|
||||
|
||||
class ServerGroupTestV213(ServerGroupTestV21):
|
||||
@@ -649,7 +652,7 @@ class ServerGroupTestV264(ServerGroupTestV213):
|
||||
|
||||
def _create_server_group_normal(self, policies=None, policy=None,
|
||||
rules=None):
|
||||
req = fakes.HTTPRequest.blank('', version=self.wsgi_api_version)
|
||||
req = fakes.HTTPRequest.member_req('', version=self.wsgi_api_version)
|
||||
sgroup = server_group_template()
|
||||
sgroup['rules'] = rules or {}
|
||||
sgroup['policy'] = policy
|
||||
@@ -674,7 +677,7 @@ class ServerGroupTestV264(ServerGroupTestV213):
|
||||
self.assertEqual(res_dict['server_group']['rules'], {})
|
||||
|
||||
def _display_server_group(self, uuid):
|
||||
req = fakes.HTTPRequest.blank('', version=self.wsgi_api_version)
|
||||
req = fakes.HTTPRequest.reader_req('', version=self.wsgi_api_version)
|
||||
group = self.controller.show(req, uuid)
|
||||
return group
|
||||
|
||||
@@ -690,7 +693,7 @@ class ServerGroupTestV264(ServerGroupTestV213):
|
||||
self.assertEqual(res_dict['server_group']['rules'], rules)
|
||||
|
||||
def test_create_affinity_server_group_with_invalid_policy(self):
|
||||
req = fakes.HTTPRequest.blank('', version=self.wsgi_api_version)
|
||||
req = fakes.HTTPRequest.member_req('', version=self.wsgi_api_version)
|
||||
sgroup = server_group_template(policy='affinity',
|
||||
rules={'max_server_per_host': 3})
|
||||
result = self.assertRaises(webob.exc.HTTPBadRequest,
|
||||
@@ -698,7 +701,7 @@ class ServerGroupTestV264(ServerGroupTestV213):
|
||||
self.assertIn("Only anti-affinity policy supports rules", str(result))
|
||||
|
||||
def test_create_anti_affinity_server_group_with_invalid_rules(self):
|
||||
req = fakes.HTTPRequest.blank('', version=self.wsgi_api_version)
|
||||
req = fakes.HTTPRequest.member_req('', version=self.wsgi_api_version)
|
||||
# A negative test for key is unknown, the value is not positive
|
||||
# and not integer
|
||||
invalid_rules = [{'unknown_key': '3'},
|
||||
@@ -718,7 +721,7 @@ class ServerGroupTestV264(ServerGroupTestV213):
|
||||
return_value=32)
|
||||
def test_create_server_group_with_low_version_compute_service(self,
|
||||
mock_get_v):
|
||||
req = fakes.HTTPRequest.blank('', version=self.wsgi_api_version)
|
||||
req = fakes.HTTPRequest.member_req('', version=self.wsgi_api_version)
|
||||
sgroup = server_group_template(policy='anti-affinity',
|
||||
rules={'max_server_per_host': 3})
|
||||
result = self.assertRaises(
|
||||
@@ -734,7 +737,7 @@ class ServerGroupTestV264(ServerGroupTestV213):
|
||||
self._create_server_group_normal(policy=policy)
|
||||
|
||||
def test_policies_since_264(self):
|
||||
req = fakes.HTTPRequest.blank('', version=self.wsgi_api_version)
|
||||
req = fakes.HTTPRequest.member_req('', version=self.wsgi_api_version)
|
||||
# 'policies' isn't allowed in request >= 2.64
|
||||
sgroup = server_group_template(policies=['anti-affinity'])
|
||||
self.assertRaises(
|
||||
@@ -742,14 +745,14 @@ class ServerGroupTestV264(ServerGroupTestV213):
|
||||
req, body={'server_group': sgroup})
|
||||
|
||||
def test_create_server_group_without_policy(self):
|
||||
req = fakes.HTTPRequest.blank('', version=self.wsgi_api_version)
|
||||
req = fakes.HTTPRequest.member_req('', version=self.wsgi_api_version)
|
||||
# 'policy' is required request key in request >= 2.64
|
||||
sgroup = server_group_template()
|
||||
self.assertRaises(self.validation_error, self.controller.create,
|
||||
req, body={'server_group': sgroup})
|
||||
|
||||
def test_create_server_group_with_illegal_policies(self):
|
||||
req = fakes.HTTPRequest.blank('', version=self.wsgi_api_version)
|
||||
req = fakes.HTTPRequest.member_req('', version=self.wsgi_api_version)
|
||||
# blank policy
|
||||
sgroup = server_group_template(policy='')
|
||||
self.assertRaises(self.validation_error, self.controller.create,
|
||||
@@ -771,7 +774,7 @@ class ServerGroupTestV264(ServerGroupTestV213):
|
||||
req, body={'server_group': sgroup})
|
||||
|
||||
def test_additional_params(self):
|
||||
req = fakes.HTTPRequest.blank('', version=self.wsgi_api_version)
|
||||
req = fakes.HTTPRequest.member_req('', version=self.wsgi_api_version)
|
||||
sgroup = server_group_template(unknown='unknown')
|
||||
self.assertRaises(self.validation_error, self.controller.create,
|
||||
req, body={'server_group': sgroup})
|
||||
@@ -786,7 +789,7 @@ class ServerGroupTestV275(ServerGroupTestV264):
|
||||
path='/os-server-groups?dummy=False&all_projects=True')
|
||||
|
||||
def test_list_server_group_additional_param(self):
|
||||
req = fakes.HTTPRequest.blank('/os-server-groups?dummy=False',
|
||||
version=self.wsgi_api_version)
|
||||
req = fakes.HTTPRequest.reader_req('/os-server-groups?dummy=False',
|
||||
version=self.wsgi_api_version)
|
||||
self.assertRaises(self.validation_error, self.controller.index,
|
||||
req)
|
||||
|
||||
@@ -240,6 +240,9 @@ class HTTPRequest(os_wsgi.Request):
|
||||
def blank(cls, *args, **kwargs):
|
||||
defaults = {'base_url': 'http://localhost/v2'}
|
||||
use_admin_context = kwargs.pop('use_admin_context', False)
|
||||
roles = kwargs.pop('roles', [])
|
||||
if use_admin_context:
|
||||
roles.append('admin')
|
||||
project_id = kwargs.pop('project_id', FAKE_PROJECT_ID)
|
||||
version = kwargs.pop('version', os_wsgi.DEFAULT_API_VERSION)
|
||||
defaults.update(kwargs)
|
||||
@@ -247,10 +250,19 @@ class HTTPRequest(os_wsgi.Request):
|
||||
out.environ['nova.context'] = FakeRequestContext(
|
||||
user_id='fake_user',
|
||||
project_id=project_id,
|
||||
is_admin=use_admin_context)
|
||||
is_admin=use_admin_context,
|
||||
roles=roles)
|
||||
out.api_version_request = api_version.APIVersionRequest(version)
|
||||
return out
|
||||
|
||||
@classmethod
|
||||
def member_req(cls, *args, **kwargs):
|
||||
return cls.blank(*args, roles=['member', 'reader'], **kwargs)
|
||||
|
||||
@classmethod
|
||||
def reader_req(cls, *args, **kwargs):
|
||||
return cls.blank(*args, roles=['reader'], **kwargs)
|
||||
|
||||
|
||||
class HTTPRequestV21(HTTPRequest):
|
||||
pass
|
||||
|
||||
@@ -128,20 +128,21 @@ class TestPolicyCheck(test.NoDBTestCase):
|
||||
self.assertEqual(set(expected_rules), set(passing_rules))
|
||||
|
||||
def test_filter_rules_non_admin(self):
|
||||
context = nova_context.RequestContext()
|
||||
context = nova_context.RequestContext(roles=['reader'])
|
||||
rule_conditions = [base_policies.PROJECT_READER_OR_ADMIN]
|
||||
expected_rules = [r.name for r in ia_policies.list_rules() if
|
||||
r.check_str in rule_conditions]
|
||||
self._check_filter_rules(context, expected_rules=expected_rules)
|
||||
|
||||
def test_filter_rules_admin(self):
|
||||
self._check_filter_rules()
|
||||
context = nova_context.RequestContext(roles=['admin'])
|
||||
self._check_filter_rules(context)
|
||||
|
||||
def test_filter_rules_instance_non_admin(self):
|
||||
db_context = nova_context.RequestContext(user_id='fake-user',
|
||||
project_id='fake-project')
|
||||
instance = fake_instance.fake_instance_obj(db_context)
|
||||
context = nova_context.RequestContext()
|
||||
context = nova_context.RequestContext(roles=['reader'])
|
||||
expected_rules = [r.name for r in ia_policies.list_rules() if
|
||||
r.check_str == base_policies.RULE_ANY]
|
||||
self._check_filter_rules(context, instance, expected_rules)
|
||||
@@ -150,11 +151,13 @@ class TestPolicyCheck(test.NoDBTestCase):
|
||||
db_context = nova_context.RequestContext(user_id='fake-user',
|
||||
project_id='fake-project')
|
||||
instance = fake_instance.fake_instance_obj(db_context)
|
||||
self._check_filter_rules(target=instance)
|
||||
context = nova_context.RequestContext(roles=['admin'])
|
||||
self._check_filter_rules(context, target=instance)
|
||||
|
||||
def test_filter_rules_instance_owner(self):
|
||||
db_context = nova_context.RequestContext(user_id='fake-user',
|
||||
project_id='fake-project')
|
||||
project_id='fake-project',
|
||||
roles=['reader'])
|
||||
instance = fake_instance.fake_instance_obj(db_context)
|
||||
rule_conditions = [base_policies.PROJECT_READER_OR_ADMIN]
|
||||
expected_rules = [r.name for r in ia_policies.list_rules() if
|
||||
|
||||
@@ -58,6 +58,16 @@ class BasePolicyTest(test.TestCase):
|
||||
|
||||
def setUp(self):
|
||||
super(BasePolicyTest, self).setUp()
|
||||
# TODO(gmann): enforce_scope and enforce_new_defaults are enabled
|
||||
# by default in the code so disable them in base test class until
|
||||
# we have deprecated rules and their tests. We have enforce_scope
|
||||
# and no-legacy tests which are explicitly enabling scope and new
|
||||
# defaults to test the new defaults and scope. In future, once
|
||||
# we remove the deprecated rules, along with refactoring the unit
|
||||
# tests we can remove overriding the oslo policy flags.
|
||||
self.flags(enforce_scope=False, group="oslo_policy")
|
||||
if not self.without_deprecated_rules:
|
||||
self.flags(enforce_new_defaults=False, group="oslo_policy")
|
||||
self.useFixture(fixtures.NeutronFixture(self))
|
||||
self.policy = self.useFixture(fixtures.RealPolicyFixture())
|
||||
|
||||
|
||||
@@ -303,10 +303,10 @@ class RealRolePolicyTestCase(test.NoDBTestCase):
|
||||
def setUp(self):
|
||||
super(RealRolePolicyTestCase, self).setUp()
|
||||
self.policy = self.useFixture(nova_fixtures.RealPolicyFixture())
|
||||
self.non_admin_context = context.RequestContext('fake', 'fake',
|
||||
roles=['member'])
|
||||
self.admin_context = context.RequestContext('fake', 'fake', True,
|
||||
roles=['admin', 'member'])
|
||||
self.non_admin_context = context.RequestContext(
|
||||
'fake', 'fake', roles=['member', 'reader'])
|
||||
self.admin_context = context.RequestContext(
|
||||
'fake', 'fake', True, roles=['admin', 'member', 'reader'])
|
||||
self.target = {}
|
||||
self.fake_policy = jsonutils.loads(fake_policy.policy_data)
|
||||
|
||||
@@ -387,6 +387,7 @@ class RealRolePolicyTestCase(test.NoDBTestCase):
|
||||
"os_compute_api:os-hypervisors:search",
|
||||
"os_compute_api:os-hypervisors:servers",
|
||||
"os_compute_api:limits:other_project",
|
||||
"os_compute_api:os-flavor-access",
|
||||
)
|
||||
|
||||
self.admin_or_owner_rules = (
|
||||
@@ -440,7 +441,6 @@ class RealRolePolicyTestCase(test.NoDBTestCase):
|
||||
"os_compute_api:os-remote-consoles",
|
||||
"os_compute_api:os-deferred-delete:restore",
|
||||
"os_compute_api:os-deferred-delete:force",
|
||||
"os_compute_api:os-flavor-access",
|
||||
"os_compute_api:os-flavor-extra-specs:index",
|
||||
"os_compute_api:os-flavor-extra-specs:show",
|
||||
"os_compute_api:os-floating-ips:add",
|
||||
|
||||
@@ -0,0 +1,23 @@
|
||||
---
|
||||
upgrade:
|
||||
- |
|
||||
The Nova service enable the API policies (RBAC) new defaults and scope by
|
||||
default. The Default value of config options ``[oslo_policy] enforce_scope``
|
||||
and ``[oslo_policy] oslo_policy.enforce_new_defaults`` have been changed
|
||||
to ``True``.
|
||||
|
||||
This means if you are using system scope token to access Nova API then
|
||||
the request will be failed with 403 error code. Also, new defaults will be
|
||||
enforced by default. To know about the new defaults of each policy
|
||||
rule, refer to the `Policy New Defaults`_. For more detail about the Nova
|
||||
API policies changes, refer to `Policy Concepts`_.
|
||||
|
||||
If you want to disable them then modify the below config options value in
|
||||
``nova.conf`` file::
|
||||
|
||||
[oslo_policy]
|
||||
enforce_new_defaults=False
|
||||
enforce_scope=False
|
||||
|
||||
.. _`Policy New Defaults`: https://docs.openstack.org/nova/latest/configuration/policy.html
|
||||
.. _`Policy Concepts`: https://docs.openstack.org/nova/latest/configuration/policy-concepts.html
|
||||
+1
-1
@@ -43,7 +43,7 @@ oslo.utils>=4.12.1 # Apache-2.0
|
||||
oslo.db>=10.0.0 # Apache-2.0
|
||||
oslo.rootwrap>=5.15.0 # Apache-2.0
|
||||
oslo.messaging>=10.3.0 # Apache-2.0
|
||||
oslo.policy>=3.7.0 # Apache-2.0
|
||||
oslo.policy>=3.11.0 # Apache-2.0
|
||||
oslo.privsep>=2.6.2 # Apache-2.0
|
||||
oslo.i18n>=5.1.0 # Apache-2.0
|
||||
oslo.service>=2.8.0 # Apache-2.0
|
||||
|
||||
Reference in New Issue
Block a user