Skip to content
Snippets Groups Projects
Commit 808be78d authored by Timm Fitschen's avatar Timm Fitschen
Browse files

Merge branch 'f-permission-docs' into 'dev'

F permission docs

See merge request !64
parents 604f9d7a d44e6ea2
No related branches found
No related tags found
2 merge requests!71Release 0.9,!64F permission docs
Pipeline #27463 passed
......@@ -15,4 +15,5 @@ build/
src/caosdb/version.py
# documentation
_apidoc
\ No newline at end of file
_apidoc
*~
......@@ -24,6 +24,8 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
### Documentation ###
* Added curator role permissions example to code gallery
## [0.8.0] - 2022-07-12
(Timm Fitschen)
......
......@@ -5,10 +5,12 @@ The Python script ``caosdb_admin.py`` should be used for administrative tasks.
Call ``caosdb_admin.py --help`` to see how to use it.
The most common task is to create a new user (in the CaosDB realm) and set a
password for the user (note that a user typically needs to be activated)::
password for the user (note that a user typically needs to be activated):
caosdb_admin.py create_user anna
caosdb_admin.py set_user_password anna
caosdb_admin.py add_user_roles anna administration
caosdb_admin.py activate_user anna
.. code:: console
$ caosdb_admin.py create_user anna
$ caosdb_admin.py set_user_password anna
$ caosdb_admin.py add_user_roles anna administration
$ caosdb_admin.py activate_user anna
Setting permissions for a curator role
======================================
The following example shows how to create and set permissions for a ``curator``
role that is allowed to insert, update, or delete any entity apart from a set of
RecordTypes and properties that define a "core data model" which can only be
altered with administration permissions.
In the following, you'll learn how to
1. create the ``curator`` role.
2. configure the ``global_entity_permissions.xml`` s.th. the ``curator`` role is
allowed to insert, update, or delete any entity by default.
3. use a Python script to override the above configuration for the entities in
the externally defined core data model.
Prerequisites
-------------
This example needs some preparations regarding your CaosDB setup that have to
(or, for the sake of simplicity, should) be done outside the actual Python
example script.
The curator role
~~~~~~~~~~~~~~~~
First, a ``curator`` role is created with a meaningful description. We'll use
``caosdb_admin.py`` for this which leads to the following command:
.. code:: console
$ caosdb_admin.py create_role "curator" "A user who is permitted to create new Records, Properties, and RecordTypes but who is not allowed to change the core data model."
To actually see how this role's permissions change, we also need a user with
this role. Assume you already have created and activated (see
:doc:`Administration <../administration>`) a ``test_curator`` user, then
``caosdb_admin.py`` is used again to assign it the correct role:
.. code:: console
$ caosdb_admin.py add_user_roles test_curator curator
.. note::
The ``test_curator`` user shouldn't have administration privileges, otherwise
the below changes won't have any effect.
The core data model and caosdb-advanced-user-tools
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
In principle, the following script works with any data model defined in a json
or yaml file (just adapt lines 39-42 accordingly). In this example, we'll use the
`metadata schema <https://github.com/leibniz-zmt/zmt-metadata-schema>`_ that was
developed by J. Schmidt at the `Leibniz Centre for Tropical Marine Research
<https://www.leibniz-zmt.de/en/>`_.
Clone the schemata into the same directory containing the below script via
.. code:: console
$ git clone https://github.com/leibniz-zmt/zmt-metadata-schema.git
Furthermore, we'll need the `CaosDB Advanced User Tools
<https://gitlab.com/caosdb/caosdb-advanced-user-tools>`_ for loading the
metadata schemata from the json files, so install them via
.. code:: console
$ pip install caosadvancedtools
The global entity permissions file
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Users with the ``curator`` role should be able to have any permission for all
entities by default. The exceptions for the core data model entities will be set
with the script below. These default settings are best done via the
``global_entities_permissions.xml`` config file (see the `server documentation
<https://docs.indiscale.com/caosdb-server/permissions.html#how-to-set-permissions>`_). Simply
add the following line to the file
.. code:: xml
<Grant priority="true" role="curator"><Permission name="*"/></Grant>
This means that, by default, all users with the ``curator`` role are **granted**
all entity permissions (including insert, update, and delete as specified in the
beginning) **with priority**. This ensures, that no normal user is allowed to
overrule these permissions (since it is granted with priority), but it can still
be denied for the core data model entities by a **deny** rule with priority. See
the server documentation on `permission
calculation <https://docs.indiscale.com/caosdb-server/permissions.html#permission-calculation>`_
for more information on which permission rules can or can't be overruled.
Your complete ``global_entities_permissions.xml`` might then look like
.. code:: xml
<globalPermissions>
<Grant priority="false" role="?OWNER?"><Permission name="*"/></Grant>
<Grant priority="false" role="?OTHER?"><Permission name="RETRIEVE:*"/></Grant>
<Grant priority="false" role="?OTHER?"><Permission name="USE:*"/></Grant>
<Grant priority="false" role="anonymous"><Permission name="RETRIEVE:*"/></Grant>
<Grant priority="true" role="curator"><Permission name="*"/></Grant>
<Deny priority="false" role="?OTHER?"><Permission name="UPDATE:*"/></Deny>
<Deny priority="false" role="?OTHER?"><Permission name="DELETE"/></Deny>
<Deny priority="true" role="?OTHER?"><Permission name="EDIT:ACL"/></Deny>
</globalPermissions>
.. note::
Note that you have to restart your CaosDB server after modifying the
``global_entities_permissions.xml``.
The code
--------
After having applied all of the above prerequisites and restarting your CaosDB
server, execute the following code.
:download:`Download full code<curator_permissions.py>`
.. literalinclude:: curator_permissions.py
#!/usr/bin/env python3
# encoding: utf-8
#
# This file is a part of the CaosDB Project.
#
# Copyright (C) 2022 Indiscale GmbH <info@indiscale.com>
# Copyright (C) 2022 Florian Spreckelsen <f.spreckelsen@indiscale.com>
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU Affero General Public License as
# published by the Free Software Foundation, either version 3 of the
# License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU Affero General Public License for more details.
#
# You should have received a copy of the GNU Affero General Public License
# along with this program. If not, see <https://www.gnu.org/licenses/>.
#
import os
import sys
import caosdb as db
from caosadvancedtools.models.parser import parse_model_from_json_schema
from caosdb import administration as admin
CURATOR = "curator"
def main():
"""Set curator role permissions: Is allowed to edit all Records; is allowed
to create new RTs and Properties and change them, but is not allowed to
change anything defined in the core data model, i.e., in the schemas.
"""
dataspace_definitions = parse_model_from_json_schema(
"zmt-metadata-schema/schemas/dataspace.schema.json")
dataset_definitions = parse_model_from_json_schema(
"zmt-metadata-schema/schemas/dataset.schema.json")
# Set general permissions. The curator users should be allowed to perform
# any transaction.
perms = admin._get_permissions(CURATOR)
general_grant_perms = [
"TRANSACTION:*"
]
for p in general_grant_perms:
g = admin.PermissionRule(action="Grant", permission=p, priority=True)
d = admin.PermissionRule(action="Deny", permission=p, priority=True)
if g in perms:
perms.remove(g)
if d in perms:
perms.remove(d)
perms.add(g)
admin._set_permissions(CURATOR, permission_rules=perms)
# Deny all permissions that could change the data model ...
core_model_deny_permissions = [
"DELETE",
"UPDATE:*",
"EDIT:ACL"
]
# ... but allow read-access and of course using the entities as parents,
# properties, ...
core_model_grant_permissions = [
"RETRIEVE:*",
"USE:*",
]
# Iterate over all entities defined in the schemas and update their access control list (ACL) accordingly.
updates = db.Container()
for model in [dataspace_definitions, dataset_definitions]:
for ent in model.values():
if ent.name in [u.name for u in updates]:
# Skip entities that have been updated already
continue
# The entity needs to be retrieved with the ACL flag to update the
# ACL down the road
ent.retrieve(flags={"ACL": None})
for d in core_model_deny_permissions:
ent.deny(role=CURATOR, priority=True, permission=d)
ent.update_acl()
ent.retrieve(flags={"ACL": None})
for g in core_model_grant_permissions:
ent.grant(role=CURATOR, priority=True, permission=g)
updates.append(ent)
ent.update_acl()
if __name__ == "__main__":
sys.exit(main())
......@@ -14,3 +14,4 @@ This chapter collects code examples which can be immediately run against an empt
:caption: The code examples:
simulation
curator-permissions
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment