Aller au contenu

GitHub SSO

Architecture

GitHub fournit l'identité, OAuth2 Proxy gère la session et Traefik applique le contrôle d'accès aux interfaces protégées.

sequenceDiagram
  participant U as Navigateur
  participant T as Traefik
  participant O as OAuth2 Proxy
  participant G as GitHub OAuth
  participant A as Interface technique
  U->>T: requête HTTPS
  T->>O: /oauth2/auth
  O-->>U: redirection GitHub si aucune session
  U->>G: authentification et consentement
  G-->>O: callback OAuth
  O-->>U: cookie de session sécurisé
  U->>T: nouvelle requête
  T->>A: accès autorisé

Paramètres actuels

Paramètre Valeur
Fournisseur GitHub
Utilisateur autorisé djayzone
Callback https://auth.lab.djayzone.com/oauth2/callback
Domaine du cookie .lab.djayzone.com
Durée du cookie 168 heures
Attributs Secure, HttpOnly, SameSite Lax
Secret oauth2-proxy-credentials, hors Git

Le middleware forward-auth interroge OAuth2 Proxy. Le middleware d'erreur transforme les réponses 401/403 en redirection vers la connexion. Les en-têtes de sécurité et la limitation de débit sont appliqués séparément.

Délégation d'identité vers Grafana

Grafana utilise une variante où l'instance OAuth2 Proxy du namespace monitoring est directement l'upstream public. Après validation de la session GitHub, elle transmet X-Forwarded-User; Grafana consomme cet en-tête via auth.proxy, auto-crée l'utilisateur et lui attribue uniquement le rôle Viewer.

Cette confiance dans l'en-tête est couplée à une NetworkPolicy : le port Grafana 3000 n'est joignable que depuis le proxy local et depuis Gatus pour le contrôle /api/health. Un client ou un autre pod ne doit jamais pouvoir contourner OAuth2 Proxy et injecter lui-même X-Forwarded-User.

Création ou rotation de l'application OAuth

  1. Dans GitHub, ouvrir les Developer settings et l'OAuth App.
  2. Conserver l'URL d'accueil sur le domaine du lab et le callback exact ci-dessus.
  3. Générer un nouveau client secret.
  4. Mettre à jour le Secret Kubernetes sans afficher les valeurs dans le terminal partagé ou les logs.
  5. Redémarrer/réconcilier OAuth2 Proxy, puis tester en navigation privée.
  6. Révoquer l'ancien secret après validation.

Le Secret doit contenir les clés attendues par le chart : client-id, client-secret et cookie-secret. Le cookie secret doit avoir une entropie suffisante.

Protéger une nouvelle interface

  1. Créer les middlewares forward-auth et auth-errors dans le namespace de l'Ingress, ou utiliser une chaîne explicitement autorisée.
  2. Référencer la chaîne dans l'annotation Traefik de l'Ingress.
  3. Vérifier que la destination n'offre pas une autre route publique non protégée.
  4. Tester utilisateur connecté, navigation privée et réponse après expiration du cookie.

Lorsqu'une application fait confiance à un en-tête d'identité transmis par le proxy, ajouter en plus une restriction réseau qui empêche tout accès direct à son backend depuis des callers non autorisés.

Dépannage

kubectl -n sso get pod,svc,ingress
kubectl -n sso logs deployment/oauth2-proxy --tail=200
kubectl -n monitoring get middleware,ingress,networkpolicy
kubectl -n monitoring logs deployment/oauth2-proxy --tail=200
kubectl -n monitoring logs deployment/monitoring-grafana -c grafana --tail=200
kubectl -n maintenance get deployment,service,ingress
kubectl -n admin-dashboard get deployment,service,ingress
Symptôme Cause probable
redirect_uri_mismatch callback GitHub différent du paramètre OAuth2 Proxy
Boucle de connexion cookie/domaines, heure système, secret incohérent ou proxy headers
403 après GitHub utilisateur non autorisé par github-user
502/503 Service OAuth2 Proxy ou application cible indisponible
Connexion acceptée mais Grafana journalise anonymous:0 auth.proxy absent, mauvais header_name ou en-tête utilisateur non transmis
Connexion acceptée mais application refusée autorisation applicative ou rôle Grafana distinct du SSO

Portée

Le SSO prouve l'identité mais ne remplace pas l'autorisation applicative. Le contrôleur de maintenance conserve sa liste fermée d'actions et Grafana son rôle applicatif.