Skip to main content
Voir en Markdown

Invitations

POST /api/auth/admin/create-user oblige un administrateur à choisir le mot de passe du nouvel utilisateur et ne lui envoie rien — praticable pour un script, inutilisable pour accueillir un client. Le flux d'invitation comble cette lacune : l'administrateur fournit { email, name, role } sans mot de passe, Sovrium envoie par e-mail un lien à usage unique, et l'invité définit son propre mot de passe puis atterrit dans une session authentifiée.

app.yaml
auth:
  strategies:
    - type: emailAndPassword
  invitationTokenExpiry: '72h' # default; accepts '30s' / '15m' / '72h' / '7d' / ms
  emailTemplates:
    invitation:
      subject: 'You are invited to join, $name'
      text: |
        Hi $name,
        $inviterName invited you to join.
        Set your password: $url
        This invitation expires in 72 hours.

Les deux points de terminaison

Point de terminaison Comportement
POST /api/auth/admin/invite-user Accepte { email, name, role } (sans mot de passe). Renvoie 200 avec { user, invitationSent: true }. 401 si l'appelant n'est pas authentifié et 404 s'il n'a pas le droit d'inviter ce rôle — jamais 403, afin que le point de terminaison ne divulgue rien ; 400 pour une saisie invalide ; 422 lorsque l'e-mail correspond déjà à un utilisateur entièrement intégré.
POST /api/auth/admin/accept-invitation Sous-tend la page publique /accept-invitation?token=.... L'invité définit un mot de passe et atterrit authentifié. 400 pour un jeton invalide, 410 pour un jeton expiré.

Les jetons réutilisent la table auth.verification (la même forme que Better Auth emploie pour la réinitialisation de mot de passe), expirent après invitationTokenExpiry72h par défaut — et sont à usage unique, consommés à la première acceptation réussie. Un rejeu est rejeté plutôt que de ré-intégrer silencieusement.

Le corps de l'e-mail est rendu à partir du modèle invitation et substitue $name, $url, $email et $inviterName.

Invitations déléguées

Par défaut, seul le rôle équivalent administrateur peut inviter. Un rôle qui déclare canInvite: true le peut également, sans devenir équivalent administrateur pour autant :

app.yaml
auth:
  roles:
    - name: engineer
      level: 80
    - name: customer-admin
      level: 40
      canInvite: true
    - name: customer-member
      level: 20
  scopeTables:
    - clients

customer-admin peut désormais intégrer ses propres collègues. Trois limites accompagnent cette autorisation, et aucune n'est configurable :

Limite Effet
Le plafond de niveau tient Le level du rôle invité doit être inférieur ou égal à celui de l'invitant. customer-admin peut inviter customer-member ou un pair, jamais engineer.
Les rôles de rang administrateur sont exclus Un rôle d'exploitation qui atteint le tableau de bord d'administration ne peut jamais être invité, quels que soient les niveaux.
Les locataires ne s'élargissent pas La personne invitée hérite des lignes de portée de l'invitant, et de rien d'autre — un invitant ne peut donc transmettre qu'un accès qu'il détient déjà.

Une invitation refusée répond 404, jamais 403 : l'appelant n'apprend donc rien sur les rôles existants.

Attribution de rôle

Sovrium fournit trois rôles par défaut — admin, member, viewer — de niveaux hiérarchiques 80, 40 et 10, et accepte des rôles personnalisés déclarés dans le bloc auth.

Une invitation porte un role explicite. Lorsqu'aucun n'est fourni à la création, un nouvel utilisateur reçoit auth.defaultRole, qui lui-même retombe sur member :

app.yaml
auth:
  strategies:
    - type: emailAndPassword
  defaultRole: viewer
  roles:
    - name: editor
      description: Can edit content
      level: 30

defaultRole est validé contre les rôles intégrés plus vos roles[] déclarés : une faute de frappe échoue donc à sovrium validate au lieu de n'attribuer discrètement rien. Le premier administrateur d'amorçage est toujours créé avec le rôle admin et une adresse vérifiée, quel que soit defaultRole.

Les rôles pilotent chaque décision d'autorisation de la plateforme : les permissions de table, l'accès par champ, l'accès aux pages et l'API d'administration elle-même. Un rôle peut être changé après coup via POST /api/auth/admin/set-role.

Depuis la console

Tout le cycle de vie est également disponible dans la console d'administration : un opérateur n'a donc jamais besoin de passer par l'API pour intégrer quelqu'un.

L'annuaire des comptes, à /_admin/users, porte une commande Invite qui ouvre la page Invitations, à /_admin/users/invitations. Vous y émettez une invitation, voyez celles encore en attente, en renvoyez une, et en révoquez une qui ne devrait pas être acceptée.

C'est une page sœur plutôt qu'un panneau de l'annuaire, pour une raison qui mérite d'être connue : invite-user crée immédiatement la ligne du compte et n'envoie le lien qu'ensuite, si bien qu'une personne invitée mais n'ayant pas encore accepté figure déjà dans l'annuaire. Afficher la liste des invitations en attente à côté de cette grille placerait la même adresse dans deux tableaux voulant dire deux choses différentes — « ce compte existe » et « cette invitation est en attente » — sans moyen de savoir à quelle ligne une commande se rapporte.

Le sélecteur de rôle propose tous les rôles que votre application peut attribuer, et pas seulement les trois intégrés : les options sont le même ensemble que celui accepté par le point de terminaison d'invitation, donc un editor ou un reviewer personnalisé déclaré sous auth.roles[] y figure. Un sélecteur plus étroit que cette limite masquerait des rôles réellement utilisés par l'application — sur une application dont les rôles sont entièrement personnalisés, les rôles intégrés n'ont aucun membre en commun avec eux — et un sélecteur plus large proposerait une valeur que le point de terminaison refusera à coup sûr.

La console est en anglais. /_admin se situe hors de l'espace de noms des langues, et aucune surface de la console n'est traduite.

Invitation ou create-user

Vous voulez Utilisez
Qu'un client choisisse son propre mot de passe invite-user — il reçoit un lien et ne voit jamais un secret défini par autrui.
Un compte de service ou d'amorçage, sans boîte e-mail create-user — vous définissez le mot de passe, rien n'est envoyé.
Accueillir alors que SMTP n'est pas configuré create-user — un e-mail d'invitation ne serait jamais délivré.

Pages connexes

Dernière mise à jour 1 septembre 2026

Cette documentation a été rédigée avec de l'IA : des erreurs ou du contenu obsolète sont donc possibles. Sovrium est en bêta. Les contributions et corrections sont les bienvenues.

Construit avec Sovrium