Browse Source

Implement system admin role in users API

This commit introduces the system admin role to the users API,
making it consistent with other system-admin policy definitions.

Subsequent patches will build on this work to expose more
functionality to domain and project users:

 - domain reader functionality
 - domain member test coverage
 - domain admin functionality
 - project user test coverage

Change-Id: I19bf5a562401100d9208f98515ce596f7ca20185
Closes-Bug: 1805406
Partial-Bug: 1748027
Partial-Bug: 968696
tags/15.0.0.0rc1
Lance Bragstad 1 year ago
parent
commit
29fb7ae395
3 changed files with 130 additions and 6 deletions
  1. +27
    -6
      keystone/common/policies/user.py
  2. +72
    -0
      keystone/tests/unit/protection/v3/test_users.py
  3. +31
    -0
      releasenotes/notes/bug-1805406-252b45d443af20b3.yaml

+ 27
- 6
keystone/common/policies/user.py View File

@@ -36,6 +36,18 @@ deprecated_list_users = policy.DeprecatedRule(
name=base.IDENTITY % 'list_users',
check_str=base.RULE_ADMIN_REQUIRED
)
deprecated_create_user = policy.DeprecatedRule(
name=base.IDENTITY % 'create_user',
check_str=base.RULE_ADMIN_REQUIRED
)
deprecated_update_user = policy.DeprecatedRule(
name=base.IDENTITY % 'update_user',
check_str=base.RULE_ADMIN_REQUIRED
)
deprecated_delete_user = policy.DeprecatedRule(
name=base.IDENTITY % 'delete_user',
check_str=base.RULE_ADMIN_REQUIRED
)

user_policies = [
policy.DocumentedRuleDefault(
@@ -97,7 +109,7 @@ user_policies = [
'method': 'GET'}]),
policy.DocumentedRuleDefault(
name=base.IDENTITY % 'create_user',
check_str=base.RULE_ADMIN_REQUIRED,
check_str=base.SYSTEM_ADMIN,
# FIXME(lbragstad): This can be considered either a system-level policy
# or a project-level policy. System administrator should have the
# ability to create users in any domain. Domain (or project)
@@ -108,25 +120,34 @@ user_policies = [
scope_types=['system'],
description='Create a user.',
operations=[{'path': '/v3/users',
'method': 'POST'}]),
'method': 'POST'}],
deprecated_rule=deprecated_create_user,
deprecated_reason=DEPRECATED_REASON,
deprecated_since=versionutils.deprecated.STEIN),
policy.DocumentedRuleDefault(
name=base.IDENTITY % 'update_user',
check_str=base.RULE_ADMIN_REQUIRED,
check_str=base.SYSTEM_ADMIN,
# FIXME(lbragstad): See the above comment about adding support for
# project scope_types in the future.
scope_types=['system'],
description='Update a user, including administrative password resets.',
operations=[{'path': '/v3/users/{user_id}',
'method': 'PATCH'}]),
'method': 'PATCH'}],
deprecated_rule=deprecated_update_user,
deprecated_reason=DEPRECATED_REASON,
deprecated_since=versionutils.deprecated.STEIN),
policy.DocumentedRuleDefault(
name=base.IDENTITY % 'delete_user',
check_str=base.RULE_ADMIN_REQUIRED,
check_str=base.SYSTEM_ADMIN,
# FIXME(lbragstad): See the above comment about adding support for
# project scope_types in the future.
scope_types=['system'],
description='Delete a user.',
operations=[{'path': '/v3/users/{user_id}',
'method': 'DELETE'}])
'method': 'DELETE'}],
deprecated_rule=deprecated_delete_user,
deprecated_reason=DEPRECATED_REASON,
deprecated_since=versionutils.deprecated.STEIN)
]



+ 72
- 0
keystone/tests/unit/protection/v3/test_users.py View File

@@ -200,3 +200,75 @@ class SystemMemberTests(base_classes.TestCaseWithBootstrap,
r = c.post('/v3/auth/tokens', json=auth)
self.token_id = r.headers['X-Subject-Token']
self.headers = {'X-Auth-Token': self.token_id}


class SystemAdminTests(base_classes.TestCaseWithBootstrap,
common_auth.AuthTestMixin,
_CommonUserTests,
_SystemUserTests):

def setUp(self):
super(SystemAdminTests, self).setUp()
self.loadapp()
self.useFixture(ksfixtures.Policy(self.config_fixture))
self.config_fixture.config(group='oslo_policy', enforce_scope=True)

self.user_id = self.bootstrapper.admin_user_id
auth = self.build_authentication_request(
user_id=self.user_id,
password=self.bootstrapper.admin_password,
system=True
)

# Grab a token using the persona we're testing and prepare headers
# for requests we'll be making in the tests.
with self.test_client() as c:
r = c.post('/v3/auth/tokens', json=auth)
self.token_id = r.headers['X-Subject-Token']
self.headers = {'X-Auth-Token': self.token_id}

def test_user_can_create_users(self):
create = {
'user': {
'name': uuid.uuid4().hex,
'domain': CONF.identity.default_domain_id
}
}

with self.test_client() as c:
c.post('/v3/users', json=create, headers=self.headers)

def test_user_can_update_users(self):
user = PROVIDERS.identity_api.create_user(
unit.new_user_ref(domain_id=CONF.identity.default_domain_id)
)

update = {'user': {'email': uuid.uuid4().hex}}
with self.test_client() as c:
c.patch(
'/v3/users/%s' % user['id'], json=update, headers=self.headers
)

def test_user_cannot_update_non_existent_user_not_found(self):
update = {'user': {'email': uuid.uuid4().hex}}
with self.test_client() as c:
c.patch(
'/v3/users/%s' % uuid.uuid4().hex, json=update,
headers=self.headers,
expected_status_code=http_client.NOT_FOUND
)

def test_user_can_delete_users(self):
user = PROVIDERS.identity_api.create_user(
unit.new_user_ref(domain_id=CONF.identity.default_domain_id)
)

with self.test_client() as c:
c.delete('/v3/users/%s' % user['id'], headers=self.headers)

def test_user_cannot_delete_non_existent_user_not_found(self):
with self.test_client() as c:
c.delete(
'/v3/users/%s' % uuid.uuid4().hex, headers=self.headers,
expected_status_code=http_client.NOT_FOUND
)

+ 31
- 0
releasenotes/notes/bug-1805406-252b45d443af20b3.yaml View File

@@ -1,3 +1,9 @@
---
features:
- |
[`bug 1805406 <https://bugs.launchpad.net/keystone/+bug/1805406>`_]
The user API now supports the ``admin``, ``member``, and
``reader`` default roles.
upgrade:
- |
[`bug 1805406 <https://bugs.launchpad.net/keystone/+bug/1805406>`_]
@@ -5,3 +11,28 @@ upgrade:
403 Forbidden`` as opposed to ``HTTP 404 Not Found`` if the calling
user doesn't have authorization to call the API. This applies consistent
authorititive policy checks to the API.

The user API uses new default policies that make it more
accessible to end users and administrators in a secure way. Please
consider these new defaults if your deployment overrides
user policies.
deprecations:
- |
[`bug 1805406 <https://bugs.launchpad.net/keystone/+bug/1805406>`_]
The user policies have been deprecated. The ``identity:get_user`` now uses
``(role:reader and system_scope:all) or user_id:%(target.user.id)s``
instead of ``rule:admin_or_owner``. The ``identity:list_users`` policy now
uses ``role:reader and system_scope:all`` instead of
``rule:admin_required``. The ``identity:create_user``,
``identity:update_user``, and ``identity:delete_user`` policies now use
``role:admin and system_scope:all`` instead of ``rule:admin_required``.
These new defaults automatically account
for system-scope and support a read-only role, making it easier
for system administrators to delegate subsets of responsibility
without compromising security. Please consider these new defaults
if your deployment overrides the user policies.
security:
- |
[`bug 1805406 <https://bugs.launchpad.net/keystone/+bug/1805406>`_]
The user API now uses system-scope and default roles to
provide better accessibility to users in a secure way.

Loading…
Cancel
Save