> ## Documentation Index
> Fetch the complete documentation index at: https://docs.solya.app/llms.txt
> Use this file to discover all available pages before exploring further.

# Authentification & multi-tenancy

> Comment la connexion, les sessions, la portée d'organisation et le changement d'organisation fonctionnent.

Cette page couvre l'identité et le modèle de tenancy de la plateforme. Pour appeler l'API en tant que
programme externe, voir [Authentification](/fr/developers/authentication).

Voici comment le login et la portée d'organisation fonctionnent :

```mermaid theme={null}
sequenceDiagram
    participant User
    participant Browser
    participant Keycloak
    participant NextAuth
    participant App
    
    User->>Browser: Visiter Solya
    Browser->>Keycloak: Initier la connexion OpenID Connect
    Keycloak->>Keycloak: Authentifier l'utilisateur
    Keycloak->>Browser: Retourner le token ID avec les groupes<br/>(tenant-*, ops-admins)
    Browser->>NextAuth: Échanger le token contre une session
    NextAuth->>App: Résoudre les groupes en organisations
    App->>App: Définir l'organisation active (choix enregistré,<br/>défaut, ou première disponible)
    App->>Browser: Session avec organizationId,<br/>rôles, permissions
    Browser->>App: Les requêtes suivantes incluent la session
    App->>App: Toutes les requêtes limitées à organizationId
```

## Connexion (Keycloak + NextAuth)

Les utilisateurs se connectent via **Keycloak** (OpenID Connect) ; **NextAuth** gère la session.
À la connexion, Solya lit les **groupes** Keycloak de l'utilisateur :

* Les groupes suivent la convention **`tenant-<org-name>`** (p. ex. `tenant-adidas`). Chacun
  se résout en une **organisation** interne.
* Le groupe spécial **`ops-admins`** marque un administrateur opérationnel.

Les organisations résolues sont stockées comme les **organisations disponibles** de l'utilisateur, et la
première devient leur **défaut**.

## La session

Une session porte l'organisation active et l'accès effectif de l'utilisateur dedans :

* `organizationId` / `organizationName` — l'organisation **active**.
* `availableOrganizationIds` — chaque organisation à laquelle l'utilisateur peut accéder.
* `defaultOrganizationId` — l'organisation de secours.
* `roles` et `effectivePermissions` — les rôles de l'utilisateur et l'union des permissions
  (directes + équipe) **dans l'organisation active**.
* `currency`, `language` et un flag `isOpsAdmin`.

## Portée d'organisation (multi-tenancy)

Chaque entité est limitée par `organizationId`, et **l'organisation active est dérivée
de la session authentifiée, jamais de l'entrée client**. Les actions serveur et les routes API
résolvent l'organisation, puis les services exécutent toutes les requêtes par rapport à elle — donc un utilisateur ou un token
ne peut jamais lire ou écrire que les données de sa propre organisation.

## Changer d'organisation

Un utilisateur appartenant à plusieurs organisations en a une **active** sélectionnée parmi (dans l'ordre) :
leur choix enregistré, puis leur défaut, puis la première disponible. Changer réactive l'organisation
active pour les requêtes suivantes ; les rôles et permissions sont ré-résolus pour l'org
nouvellement active.

## Deux façons de se connecter

| Appelant                | Mécanisme                                                                                                                                        |
| ----------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------ |
| **Navigateur (humain)** | Cookie de session NextAuth établi via Keycloak                                                                                                   |
| **Programme / agent**   | Token de compte de service `Authorization: Bearer solya_sa_…` (limité à l'organisation) — voir [Authentification](/fr/developers/authentication) |

Les deux se résolvent au même contexte limité à l'organisation, donc les mêmes points de terminaison servent les deux.
Les actions serveur appliquent l'authentification (et les permissions optionnelles) ; les routes API font de même et
prennent en charge en plus un mode bearer interne pour les services internes.
