\ No newline at end of file
diff --git a/SampleService.spec b/SampleService.spec
index b5a58c8e..b5146fe1 100644
--- a/SampleService.spec
+++ b/SampleService.spec
@@ -226,6 +226,12 @@ module SampleService {
> 0: public read.
0: No change (the default).
< 0: private.
+ at_least - false, the default, indicates that the users should get the exact permissions
+ as specified in the user lists, which may mean a reduction in permissions. If true,
+ users that already exist in the sample ACLs will not have their permissions reduced
+ as part of the ACL update unless they are in the remove list. E.g. if a user has
+ write permissions and read permissions are specified in the update, no changes will
+ be made to the user's permission.
as_admin - update the sample acls regardless of sample ACL contents as long as the user has
full service administration permissions.
*/
@@ -236,6 +242,7 @@ module SampleService {
list read;
list remove;
int public_read;
+ boolean at_least;
boolean as_admin;
} UpdateSampleACLsParams;
diff --git a/lib/SampleService/SampleServiceClient.py b/lib/SampleService/SampleServiceClient.py
index 68d0bef3..5e4cd982 100644
--- a/lib/SampleService/SampleServiceClient.py
+++ b/lib/SampleService/SampleServiceClient.py
@@ -280,7 +280,14 @@ def update_sample_acls(self, params, context=None):
of users that will have all privileges removed. Default none.
public_read - an integer that determines whether the sample will
be set to publicly readable: > 0: public read. 0: No change (the
- default). < 0: private. as_admin - update the sample acls
+ default). < 0: private. at_least - false, the default, indicates
+ that the users should get the exact permissions as specified in
+ the user lists, which may mean a reduction in permissions. If
+ true, users that already exist in the sample ACLs will not have
+ their permissions reduced as part of the ACL update unless they
+ are in the remove list. E.g. if a user has write permissions and
+ read permissions are specified in the update, no changes will be
+ made to the user's permission. as_admin - update the sample acls
regardless of sample ACL contents as long as the user has full
service administration permissions.) -> structure: parameter "id"
of type "sample_id" (A Sample ID. Must be globally unique. Always
@@ -289,8 +296,9 @@ def update_sample_acls(self, params, context=None):
type "user" (A user's username.), parameter "read" of list of type
"user" (A user's username.), parameter "remove" of list of type
"user" (A user's username.), parameter "public_read" of Long,
- parameter "as_admin" of type "boolean" (A boolean value, 0 for
- false, 1 for true.)
+ parameter "at_least" of type "boolean" (A boolean value, 0 for
+ false, 1 for true.), parameter "as_admin" of type "boolean" (A
+ boolean value, 0 for false, 1 for true.)
"""
return self._client.call_method('SampleService.update_sample_acls',
[params], self._service_ver, context)
diff --git a/lib/SampleService/SampleServiceImpl.py b/lib/SampleService/SampleServiceImpl.py
index 1871419b..adab94d1 100644
--- a/lib/SampleService/SampleServiceImpl.py
+++ b/lib/SampleService/SampleServiceImpl.py
@@ -54,7 +54,7 @@ class SampleService:
######################################### noqa
VERSION = "0.1.0-alpha21"
GIT_URL = "https://github.com/mrcreosote/sample_service.git"
- GIT_COMMIT_HASH = "b6daa022f7eb7eb7a48156022619b21febf103f4"
+ GIT_COMMIT_HASH = "67b70bb587fbf1212a06c716e2e44b0d161cd4c7"
#BEGIN_CLASS_HEADER
#END_CLASS_HEADER
@@ -362,7 +362,14 @@ def update_sample_acls(self, ctx, params):
of users that will have all privileges removed. Default none.
public_read - an integer that determines whether the sample will
be set to publicly readable: > 0: public read. 0: No change (the
- default). < 0: private. as_admin - update the sample acls
+ default). < 0: private. at_least - false, the default, indicates
+ that the users should get the exact permissions as specified in
+ the user lists, which may mean a reduction in permissions. If
+ true, users that already exist in the sample ACLs will not have
+ their permissions reduced as part of the ACL update unless they
+ are in the remove list. E.g. if a user has write permissions and
+ read permissions are specified in the update, no changes will be
+ made to the user's permission. as_admin - update the sample acls
regardless of sample ACL contents as long as the user has full
service administration permissions.) -> structure: parameter "id"
of type "sample_id" (A Sample ID. Must be globally unique. Always
@@ -371,8 +378,9 @@ def update_sample_acls(self, ctx, params):
type "user" (A user's username.), parameter "read" of list of type
"user" (A user's username.), parameter "remove" of list of type
"user" (A user's username.), parameter "public_read" of Long,
- parameter "as_admin" of type "boolean" (A boolean value, 0 for
- false, 1 for true.)
+ parameter "at_least" of type "boolean" (A boolean value, 0 for
+ false, 1 for true.), parameter "as_admin" of type "boolean" (A
+ boolean value, 0 for false, 1 for true.)
"""
# ctx is the context object
#BEGIN update_sample_acls
diff --git a/test/SampleService_test.py b/test/SampleService_test.py
index 17e293e3..b3fa5f7a 100644
--- a/test/SampleService_test.py
+++ b/test/SampleService_test.py
@@ -1653,7 +1653,7 @@ def _update_acls_tst(sample_port, kafka, token, as_admin):
'admin': [USER2],
'write': [USER_NO_TOKEN1, USER_NO_TOKEN2, USER3],
'read': [USER_NO_TOKEN3, USER4],
- 'public_read': 1
+ 'public_read': 0
})
_update_acls(url, token, {
@@ -1663,7 +1663,7 @@ def _update_acls_tst(sample_port, kafka, token, as_admin):
'read': [USER_NO_TOKEN2],
'remove': [USER3],
'public_read': 390,
- 'as_admin': 1 if as_admin else 0
+ 'as_admin': 1 if as_admin else 0,
})
_assert_acl_contents(url, id_, TOKEN1, {
@@ -1683,6 +1683,53 @@ def _update_acls_tst(sample_port, kafka, token, as_admin):
])
+def test_update_acls_with_at_least(sample_port, kafka):
+ _update_acls_tst_with_at_least(sample_port, kafka, TOKEN1, False) # owner
+ _update_acls_tst_with_at_least(sample_port, kafka, TOKEN2, False) # admin
+ _update_acls_tst_with_at_least(sample_port, kafka, TOKEN5, True) # as_admin = True
+
+
+def _update_acls_tst_with_at_least(sample_port, kafka, token, as_admin):
+ _clear_kafka_messages(kafka)
+ url = f'http://localhost:{sample_port}'
+
+ id_ = _create_generic_sample(url, TOKEN1)
+
+ _replace_acls(url, id_, TOKEN1, {
+ 'admin': [USER2],
+ 'write': [USER_NO_TOKEN1, USER_NO_TOKEN2, USER3],
+ 'read': [USER_NO_TOKEN3, USER4],
+ 'public_read': 0
+ })
+
+ _update_acls(url, token, {
+ 'id': str(id_),
+ 'admin': [USER4],
+ 'write': [USER2, USER_NO_TOKEN3],
+ 'read': [USER_NO_TOKEN2, USER5],
+ 'remove': [USER3],
+ 'public_read': 390,
+ 'as_admin': 1 if as_admin else 0,
+ 'at_least': 1,
+ })
+
+ _assert_acl_contents(url, id_, TOKEN1, {
+ 'owner': USER1,
+ 'admin': [USER2, USER4],
+ 'write': [USER_NO_TOKEN1, USER_NO_TOKEN2, USER_NO_TOKEN3],
+ 'read': [USER5],
+ 'public_read': 1
+ }, print_resp=True)
+
+ _check_kafka_messages(
+ kafka,
+ [
+ {'event_type': 'NEW_SAMPLE', 'sample_id': id_, 'sample_ver': 1},
+ {'event_type': 'ACL_CHANGE', 'sample_id': id_},
+ {'event_type': 'ACL_CHANGE', 'sample_id': id_},
+ ])
+
+
def test_update_acls_fail_no_id(sample_port):
url = f'http://localhost:{sample_port}'