Aller au contenu

6. Les droits

Trois niveaux, du plus large au plus fin. Les trois s’appliquent dans la couche d’accès aux données, jamais dans l’écran ni dans l’API : un point d’entrée oublié ne peut pas ouvrir une brèche, et un utilisateur qui appelle l’API directement obtient exactement ce que l’interface lui montrerait.

Niveau 1 : qui peut toucher au modèle

acl.json, à la racine du module.

{
"library_title": {
"read": ["library_reader", "library_librarian", "kws_admin"],
"create": ["library_librarian", "kws_admin"],
"write": ["library_librarian", "kws_admin"],
"unlink": ["library_librarian", "kws_admin"]
},
"library_member": {
"read": ["library_librarian", "kws_admin"],
"create": ["library_librarian", "kws_admin"],
"write": ["library_librarian", "kws_admin"],
"unlink": ["kws_admin"]
}
}

Notez la deuxième entrée : un lecteur ne voit pas la liste des adhérents. Ce n’est pas un écran caché, c’est un droit absent, et l’API le refuse aussi.

Quatre verbes : lire, créer, modifier, supprimer. Un groupe absent d’une liste n’a pas le droit.

Niveau 2 : quelles lignes

Une règle d’enregistrement filtre les lignes visibles, par groupe.

from kewos.security import RecordRule
from kewos.auth.context import current_user_id
def _own_loans(cls):
"""A reader sees the loans they took out, and no one else's."""
return cls.created_by_id == current_user_id()
_LOAN_RULES = (
RecordRule(
name="library_loan_own",
domain=_own_loans,
groups=("library_reader",),
),
)

Puis on l’attache au modèle :

registry.register_model(
"library_loan",
module="library",
fields=[...],
record_rules=_LOAN_RULES,
)

Deux propriétés à connaître, et elles surprennent :

  • Une règle ne s’applique qu’aux porteurs de ses groupes. Un utilisateur sans le groupe visé n’est pas filtré par cette règle.
  • Plusieurs règles applicables se combinent par ET. Un utilisateur qui porte deux groupes visés par deux règles voit l’intersection. C’est volontairement restrictif : le résultat d’une erreur est qu’on voit moins, jamais plus.

Si vous voulez qu’une condition élargisse la visibilité, mettez-la dans un OU à l’intérieur d’une seule règle, jamais dans une seconde règle.

Niveau 3 : quels champs

Une règle de champ cache ou verrouille une colonne.

from kewos.security import FieldRule
_MEMBER_FIELD_RULES = (
FieldRule(field="email", read=("library_librarian", "kws_admin"),
write=("library_librarian", "kws_admin")),
)

Attachée de la même façon, par field_rules=.

Un utilisateur sans le droit de lecture ne reçoit pas la colonne, ni dans l’API ni dans l’écran. Il ne la voit pas grisée : elle n’existe pas pour lui.

Déclarer les groupes

Les groupes de votre module doivent exister. Déclarez-les avec leurs libellés, et donnez-leur une clé de traduction group.<nom>.

Un utilisateur reçoit ses groupes dans Paramètres → Utilisateurs. En développement :

Fenêtre de terminal
kewos access grant --user <login> --group library_librarian --database-url "$KEWOS_DATABASE_URL"

Vérifier

Le seul test qui vaut est celui-ci : connectez-vous avec un compte qui ne porte que library_reader et regardez. Un administrateur voit toujours tout, donc tester en administrateur ne prouve rien.

Et ensuite

Les états.