Configuration oauthsonas

La configuration YAML est décodée de façon stricte : les champs inconnus font échouer le démarrage au lieu d'être ignorés. Validez sans démarrer le serveur :

go run ./cmd/oauthsonas --config config.yaml --check-config

Le dépôt fournit config.example.yaml avec un client public dashboard et des personas plateforme, staff et client.

Champs de premier niveau

ChampRôle
issuerURL d'issuer OIDC exacte (exemple : http://127.0.0.1:8181)
api_audienceAudience apposée sur les access tokens
token_ttlDurée de vie des access tokens (et associés)
authorization_code_ttlDurée de vie des codes d'autorisation
refresh_token_ttlDurée de vie des refresh tokens
claimsSurcharges optionnelles des noms de claims (voir ci-dessous)
clientsClients OAuth enregistrés
personasIdentités sélectionnables sur la page d'autorisation
allowed_rolesVocabulaire optionnel ; si défini, les rôles des personas doivent en faire partie

Clients

clients:
  - id: dashboard
    name: Optimi Dashboard
    public: true
    redirect_uris:
      - http://127.0.0.1:5173/auth/callback
    post_logout_redirect_uris:
      - http://127.0.0.1:5173/
    allowed_origins:
      - http://127.0.0.1:5173

Règles :

  • redirect_uris et post_logout_redirect_uris sont des valeurs à correspondance exacte. Les paramètres de requête fixes sont autorisés ; les fragments ne le sont pas.
  • allowed_origins autorise le CORS navigateur uniquement pour les origines listées.
  • Les réponses token et userinfo appliquent le CORS propre au client ; la découverte et le JWKS appliquent le CORS uniquement à l'union des origines enregistrées — jamais *.
  • Les clients publics (comme dans l'exemple) exigent S256 PKCE.

Personas

Les personas sont les identités qu'un développeur choisit sur la page d'autorisation. Chacune a besoin d'un id unique et d'au moins un rôle :

personas:
  - id: acme-admin
    subject: oauthsonas|acme-admin
    email: admin@acme.dev.optimi.test
    name: Acme Administrator
    organization_id: org_acme
    roles: [customer-admin]

  - id: platform-admin
    subject: oauthsonas|platform-admin
    email: platform-admin@dev.optimi.test
    name: Platform Admin
    roles: [platform-admin]
ChampRequisNotes
idouiSélecteur / valeur de formulaire stable
subjectouiJWT sub
emailouiÉmis lorsque le scope email est accordé
nameouiÉmis lorsque le scope profile est accordé
rolesouiAu moins un nom de rôle
organization_idnonDevient org_id (ou le claim configuré) s'il est défini
membershipsnonListe optionnelle d'appartenances multi-org

Les rôles sont portés comme noms uniquement. oauthsonas n'expand jamais les rôles en permissions applicatives — cela reste dans la partie cliente.

Ajoutez un persona en appendant une entrée unique sous personas. Définissez optionnellement une liste de premier niveau allowed_roles si un projet veut une validation de vocabulaire au chargement de la config ; sinon tout nom de rôle non vide est valide.

Claims applicatifs

Les attributs de persona sont émis comme claims JWT et userinfo. Défauts :

Champ personaNom de claim par défautQuand il est émis
rolesrolesToujours (au moins un rôle requis)
organization_idorg_idUniquement s'il est défini sur le persona
membershipsmembershipsUniquement s'ils sont définis sur le persona

Exemple de payload d'access token avec les défauts :

{
  "roles": ["customer-admin"],
  "org_id": "org_acme"
}

org_id est omis pour les personas staff sans organization_id. memberships est omis sauf si le persona les liste.

Surcharger les noms de claims

claims:
  roles: roles
  memberships: memberships
  org_id: org_id

Utilisez des URL namespacées lorsqu'un consommateur exige des claims personnalisés style Auth0 :

claims:
  roles: https://example.com/roles
  memberships: https://example.com/memberships
  org_id: org_id

Règles :

  • Les noms de claims doivent être non vides et sans espaces.
  • Les trois noms configurés doivent être distincts les uns des autres.
  • Les mêmes noms apparaissent dans les access tokens, ID tokens, userinfo et claims_supported de la découverte.
  • Les champs YAML des personas (roles, organization_id, memberships) restent les mêmes ; seules les clés de claims JWT émises changent.
  • Les noms de claims personnalisés ne doivent pas entrer en collision avec les claims JWT/OIDC standard (par exemple sub, email, scope, client_id).

Claims de profil gated par scope

  • email et email_verified exigent le scope email.
  • name exige profile.
  • Les scopes OAuth restent des scopes protocole et n'encodent pas de permissions applicatives.

Clés et forme des tokens

Le serveur génère une clé RSA 2048 bits au démarrage et publie la composante publique sur /.well-known/jwks.json. Les access et ID tokens sont signés en RS256 et incluent un kid de durée de vie du processus. Aucun JWT non signé ni symétrique n'est produit.

Les valeurs JWT aud sont sérialisées en tableaux JSON par Fosite (JWT/OIDC valide) :

  • Les access tokens ciblent l'api_audience configurée.
  • Les ID tokens ciblent l'ID client.

Exemple : configuration minimale complète

issuer: http://127.0.0.1:8181
api_audience: https://api.example.test
token_ttl: 15m
authorization_code_ttl: 5m
refresh_token_ttl: 8h

clients:
  - id: dashboard
    name: Local Dashboard
    public: true
    redirect_uris:
      - http://127.0.0.1:5173/auth/callback
    post_logout_redirect_uris:
      - http://127.0.0.1:5173/
    allowed_origins:
      - http://127.0.0.1:5173

personas:
  - id: developer
    subject: oauthsonas|developer
    email: dev@example.test
    name: Local Developer
    roles: [customer-admin]
    organization_id: org_local

Suite