Construction d'un SaaS multi-locataire : espaces de travail, rôles, facturation et isolation

Comment concevoir des espaces de travail, un contrôle d'accès basé sur les rôles, des niveaux de facturation et une isolation des locataires pour un SaaS évolutif. Architecture pratique de DigiForge.

DFL'équipe DigiForgeJul 20, 202610 min de lecture
Blocs interconnectés lumineux abstraits sur fond sombre représentant une architecture SaaS multi-locataire.

Le SaaS multi-tenant est l'architecture par défaut pour toute plateforme B2B qui ambitionne de dépasser une poignée de clients. Mais le diable se cache dans les détails : la manière dont vous modélisez les espaces de travail, assignez les rôles, structurez la facturation et isolez les locataires détermine si votre plateforme évolue en douceur ou s'effondre sous la complexité. Chez DigiForge, nous avons construit et reconstruit ces systèmes sur des dizaines de produits SaaS. Voici ce que nous avons appris.

Espaces de travail : l'unité centrale d'organisation

Un espace de travail est un conteneur logique qui regroupe utilisateurs, données et configuration pour un seul client (ou une équipe au sein d'un client). Nous avons vu des équipes confondre espaces de travail avec comptes de facturation ou même avec des projets — ne le faites pas. Conservez l'espace de travail comme périmètre fondamental du locataire, et superposez d'autres concepts par-dessus.

Décisions de conception clés :

  • Hiérarchique ou plat ? Certaines plateformes ont besoin d'espaces de travail imbriqués (par exemple, une entreprise avec plusieurs départements). Nous recommandons une hiérarchie à deux niveaux : organisation (entité de facturation) et espace de travail (unité d'équipe). Évitez les imbrications plus profondes sauf en cas d'absolue nécessité — cela complique l'héritage des rôles et l'accès aux données.
  • Identifiants uniques : Utilisez un slug lisible (comme acme ou acme-marketing) pour l'espace de travail dans les URL, mais basez-vous toujours sur un UUID en interne. Les slugs peuvent changer ; les UUID ne le devraient pas.
  • Suppression logicielle avec période de grâce : Supprimer un espace de travail est une action radicale. Implémentez une suppression logicielle de 30 jours pour permettre aux utilisateurs de récupérer les données. Arrêtez la facturation immédiatement mais conservez les données jusqu'à l'expiration de la période de grâce.

Lorsqu'un nouvel utilisateur s'inscrit, réfléchissez au flux d'onboarding. Doit-il d'abord créer un espace de travail, ou peut-il explorer un bac à sable ? Nous préférons un flux guidé où l'utilisateur crée une organisation, puis son premier espace de travail, et est immédiatement invité à ajouter des coéquipiers. Cela réduit les frictions et établit l'attente que la plateforme est collaborative.

Une erreur courante consiste à attacher directement les plans de facturation aux espaces de travail. Attachez plutôt la facturation à une organisation qui contient un ou plusieurs espaces de travail. Cela permet aux entreprises d'avoir une seule facture tout en donnant à chaque équipe son propre espace de travail.

Rôles et permissions : granulaires, mais pas trop

Le contrôle d'accès basé sur les rôles (RBAC) est la norme de l'industrie, mais la granularité compte. Chez DigiForge, nous commençons généralement avec trois rôles intégrés — Admin, Membre, Observateur — et permettons des rôles personnalisés pour les forfaits avancés. Le rôle Admin a un contrôle total sur l'espace de travail, les Membres peuvent créer et modifier la plupart des ressources, et les Observateurs ne peuvent que lire.

Là où les choses se compliquent, c'est avec le périmètre des permissions. Les permissions devraient être limitées à l'espace de travail par défaut, mais vous pourriez avoir besoin de permissions au niveau de l'organisation (par exemple, gérer la facturation) ou même d'un accès en lecture entre espaces de travail pour des rapports consolidés. Modélisez les permissions comme un ensemble de paires action:ressource et assignez-les aux rôles. Stockez les affectations dans une table de jointure : (workspace_id, user_id, role_id).

Conseil de pro : Évitez de vérifier les autorisations uniquement au niveau de l'application. Déléguez autant que possible la logique d'autorisation à votre base de données en utilisant la sécurité au niveau des lignes (RLS) ou un moteur de politiques comme OPA. Cela réduit le risque qu'un bogue dans votre couche web expose les données d'un autre utilisateur.

Un modèle qui nous a bien servi est de mettre en cache le rôle de l'utilisateur dans un jeton de session (JWT) plutôt que d'interroger la base de données à chaque requête. Mais attention : si vous mettez en cache les rôles dans les JWT, vous devez disposer d'un mécanisme pour invalider les jetons lorsqu'un rôle change (par exemple, une expiration courte du jeton ou une liste de blocage).

Pensez également à l'héritage des rôles : un administrateur d'organisation doit-il automatiquement être administrateur dans tous les espaces de travail ? Notre règle empirique : les rôles d'organisation fournissent un plafond, mais les rôles d'espace de travail peuvent être plus restrictifs. Par exemple, un administrateur d'organisation peut accéder à n'importe quel espace de travail, mais un administrateur d'espace de travail ne peut pas accéder à la facturation.

Facturation et modèles de tarification : métadonnées, pas logique métier

La facturation est là où la multi-location devient concrète. Votre modèle de tarification (par siège, par espace de travail, basé sur l'utilisation ou par paliers) doit être reflété dans votre modèle de données, mais votre système de facturation doit être découplé de votre application principale. Utilisez un fournisseur de facturation tiers (Stripe, Recurly, Chargebee) et conservez uniquement l'ID d'abonnement et l'ID de plan dans votre base de données.

Nous recommandons l'approche suivante pour la base de données :

  1. Une table plans qui définit le slug du plan, le prix et les indicateurs de fonctionnalités (par exemple, max_users, storage_gb, api_rate_limit).
  2. Une table organizations qui possède un current_plan_id et un billing_provider_subscription_id. Liez les organisations aux espaces de travail via une table de jointure.
  3. Une table features (ou une simple colonne JSON) qui stocke les dérogations. Par exemple, si un client négocie un tarif personnalisé, remplacez le prix du plan au niveau de l'organisation.

La partie la plus difficile est de limiter l'accès en fonction du plan. Vous avez deux choix : appliquer les limites dans l'application (vérifier max_users avant d'inviter) ou les appliquer via des compteurs de lignes et des déclencheurs dans la base de données. Nous préférons l'application au niveau de l'application car elle produit de meilleurs messages d'erreur pour l'utilisateur, mais nous ajoutons toujours un travail de réconciliation nocturne qui signale les organisations dépassant leurs limites.

Les mises à niveau et les rétrogradations de plan nécessitent une gestion minutieuse. Lorsqu'un client passe à un plan supérieur, accordez immédiatement l'accès aux nouvelles fonctionnalités mais proratisez la facturation via votre fournisseur. En cas de rétrogradation, vous devez décider : bloquer l'accès aux fonctionnalités qui dépassent le nouveau plan, ou autoriser une période de grâce ? Nous recommandons une période de grâce correspondant au cycle de facturation en cours, après quoi vous appliquez les restrictions.

Une leçon du terrain : ne laissez jamais les échecs de facturation entraîner une perte de données. Si un paiement échoue, dégradez progressivement (par exemple, restreignez les opérations d'écriture) mais ne supprimez pas les données. Votre client finira par payer.

Isolation des locataires : partagé vs. silo

L'isolation est la décision architecturale la plus lourde de conséquences. Le compromis standard se situe entre une base de données partagée (une seule base pour tous les locataires, avec une colonne tenant_id sur chaque table) et une base de données par locataire (chaque espace de travail possède sa propre base de données). Nous avons expérimenté les deux et avons opté pour une approche hybride dans la plupart des projets.

  • Partagé avec RLS strict : Idéal pour les petits et moyens locataires (moins de 10 000 utilisateurs chacun). La sécurité au niveau des lignes est intégrée à Postgres, et nous utilisons une variable de session (app.tenant_id) pour filtrer chaque requête. C'est la solution la plus simple à exploiter et à mettre à niveau.
  • Base de données par locataire : Nécessaire lorsque les locataires exigent une conformité stricte (HIPAA, SOC 2, RGPD en matière de résidence des données) ou lorsque l'application est intensive en E/S par locataire. La surcharge opérationnelle est réelle : les migrations de schéma doivent être appliquées à des centaines de bases de données, mais des outils comme Flyway et une CI automatisée rendent cela gérable.
  • Schéma par locataire : Un juste milieu utilisant des schémas séparés au sein d'une même base de données. Cela offre plus d'isolation qu'une table partagée, mais moins de surcharge opérationnelle que des bases de données complètes. Nous utilisons cette approche pour nos offres de niveau inférieur et passons les clients à une base de données par locataire si nécessaire.

Quelle que soit la stratégie d'isolation, n'autorisez jamais un accès direct à la base de données depuis le client. Acheminez toujours via une couche API qui applique l'identité du locataire. Et pour l'amour de votre équipe d'astreinte : n'utilisez jamais, au grand jamais, tenant_id dans les URL sans valider que l'utilisateur authentifié appartient à ce locataire.

La migration des données entre les niveaux d'isolation est une réalité. Par exemple, lorsqu'un locataire dépasse la capacité de la base de données partagée, vous devrez peut-être le migrer vers une base de données dédiée. Planifiez cela tôt : écrivez un script de migration qui exporte et importe les données, et testez-le avec des données proches de la production. Il doit pouvoir s'exécuter sans temps d'arrêt en utilisant une approche blue-green.

Provisionnement automatisé : laissez la machine faire le travail

Créer manuellement de nouveaux locataires peut fonctionner pour les dix premiers clients, mais cela ne passe pas à l'échelle. Comme le récent dépôt de brevet de ContractorHUB le souligne, l'implémentation sans intervention humaine est un différenciateur clé pour les SaaS multi-locataires [1]. Nous avons construit des workflows de provisionnement qui automatisent tout, de la création de bases de données (ou le clonage de schémas) à l'initialisation des données par défaut et l'envoi d'e-mails de bienvenue.

Un pipeline de provisionnement automatisé typique :

  1. L'utilisateur s'inscrit, crée une organisation et sélectionne un plan.
  2. Un webhook de votre fournisseur de facturation déclenche un job de provisionnement (par exemple, une fonction serverless ou un Job Kubernetes).
  3. Le job crée la couche d'isolation du locataire (schéma ou base de données), exécute les migrations initiales et remplit les rôles et paramètres par défaut.
  4. Un second job envoie un e-mail avec les instructions de connexion et les prochaines étapes.
  5. L'utilisateur est redirigé vers le nouvel espace de travail, entièrement fonctionnel, en quelques secondes.

L'idempotence est ici non négociable. Si le job de provisionnement échoue en cours de route, il doit pouvoir être relancé en toute sécurité. Nous encapsulons l'ensemble du processus dans une machine d'état avec une colonne provisioning_status sur la ligne de l'organisation : pending → creating → active → failed. Les états d'échec sont envoyés dans une file d'attente de lettres mortes pour intervention humaine.

N'oubliez pas de provisionner l'infrastructure de support : enregistrements DNS pour les domaines personnalisés, préchauffeurs de cache CDN, limites de débit API par locataire et alertes de surveillance. Automatisez tout ce qui peut être scripté, car les étapes manuelles seront oubliées sous pression.

Conclusion : L'état d'esprit multi-locataire

La multi-location ne s'ajoute pas après le lancement. Elle doit guider votre modèle de données, votre contrôle d'accès, votre intégration de facturation et votre stratégie de déploiement dès le premier jour. La bonne nouvelle : si vous maîtrisez ces quatre piliers—espaces de travail, rôles, facturation, isolation—le reste de votre SaaS devient remarquablement plus facile à construire et à maintenir.

Chaque SaaS est différent, mais les schémas ci-dessus ont bien fonctionné pour nous dans divers secteurs. Que vous débutiez votre MVP ou que vous passiez à l'échelle avec des milliers de locataires, nous vous encourageons à réfléchir en profondeur à ces décisions. Et si vous souhaitez un regard extérieur sur votre architecture, nous sommes toujours ravis de l'examiner.

#multi-locataire#saas#espaces-de-travail#rôles#facturation#isolation#provisionnement
DF

L'équipe DigiForge

L'équipe d'ingénierie de DigiForge — qui conçoit des sites web modernes, des modules et de l'automatisation, et écrit sur l'art de livrer des produits web rapides et durables.

Discutons-en

Vous avez un projet
en tête ?

Dites-nous ce que vous construisez — nous établirons un plan clair et l'approche appropriée pour votre produit.

Lancer votre projet