In diesem Blogpost widme ich mich dem Thema Authentifizierung und Autorisierung. Besonders in einem Kubernetes-Cluster, selbst in einem Heimsetup, ist es wichtig, dass nur autorisierte Benutzer Zugriff auf sensible Daten und Anwendungen haben. Um dies zu gewährleisten, nutze ich in meinem Setup Authentik in Kombination mit dem OAuth2-Proxy, um meine Anwendungen abzusichern. Als Beispiel zeige ich dir, wie ich das Kubernetes-Dashboard schütze.

Warum Authentifizierung und Autorisierung?
Wenn du Anwendungen in deinem Cluster betreibst, ist es entscheidend, dass nur befugte Personen darauf zugreifen können. Besonders wenn dein Cluster von außen erreichbar ist, sind starke Authentifizierungs- und Autorisierungslösungen notwendig. Der Unterschied zwischen diesen beiden Begriffen:
- Authentifizierung: Wer bist du? (z.B. durch Login via OAuth2)
- Autorisierung: Was darfst du tun? (Rollen und Berechtigungen im System)
Für dieses Setup verwende ich Authentik, eine Open-Source-Lösung für Authentifizierung, die mit OAuth2 arbeitet. Um den Zugriff auf Anwendungen zu steuern, nutze ich den OAuth2-Proxy, der Anfragen abfängt und überprüft, ob ein Nutzer authentifiziert ist.
Authentik: Das zentrale Authentifizierungssystem
Authentik ist eine moderne Open-Source-Auth-Lösung, die mir erlaubt, OAuth2, SSO (Single-Sign-On) und weitere Authentifizierungsmechanismen in meinem Cluster zu integrieren. Es ist besonders flexibel und bietet die Möglichkeit, externe Anwendungen, wie das Kubernetes-Dashboard, über OAuth2 abzusichern.
Vorteile von Authentik:
- OAuth2-Unterstützung: Ideal, um externe Dienste zu sichern.
- SSO (Single-Sign-On): Einmal einloggen und auf mehrere Anwendungen zugreifen.
- Einfach erweiterbar: Unterstützt viele Protokolle wie LDAP, SAML und OAuth2.
Die Installation und Konfiguration von Authentik habe ich über FluxCD automatisiert, um es einfach in meinen GitOps-Workflow zu integrieren. Hier ist ein Beispiel für die grundlegende Installation in meinem Setup:
apiVersion: helm.toolkit.fluxcd.io/v2beta1
kind: HelmRelease
metadata:
name: authentik
namespace: authentik
spec:
spec:
chart: authentik
version: 2024.8.0 # auto-update to semver bugfixes only
sourceRef:
kind: HelmRepository
name: authentik
namespace: default
values:
...
Authentic benötigt zusätzlich eine Datenbank, ich habe mich für Postgres entschieden und eingerichtet. Ich nutze dafür cloudnative-pg von truecharts. Damit bekomme ich einen Kubernetes Operator, der mir Postgres-Instanzen im Namespace installieren kann.
OAuth2-Proxy: Der Authentifizierungs-Filter
Der OAuth2-Proxy ist ein kleines, aber leistungsstarkes Tool, das sich zwischen den Benutzer und die Anwendung schaltet. Es überprüft, ob der Nutzer über OAuth2 authentifiziert wurde, bevor er Zugriff auf die Anwendung erhält. In Kombination mit Authentik sorgt dies für eine nahtlose Authentifizierung in deinem Kubernetes-Cluster.
Warum OAuth2-Proxy?
- Absicherung von Anwendungen: OAuth2-Proxy stellt sicher, dass nur authentifizierte Nutzer auf bestimmte Services zugreifen können.
- Flexibel: Kann mit verschiedenen OAuth2-Providern wie Authentik, Google oder GitHub verwendet werden.
Auch der OAuth2-Proxy wird bei mir über FluxCD installiert:
apiVersion: helm.toolkit.fluxcd.io/v2beta1
kind: HelmRelease
metadata:
name: oauth2-proxy
namespace: oauth
spec:
chart:
spec:
chart: oauth2-proxy
version: 7.7.16 # auto-update to semver bugfixes only
sourceRef:
kind: HelmRepository
name: oauth2-proxy
namespace: default
values:
...
Kubernetes-Dashboard absichern
Das Kubernetes-Dashboard ist ein nützliches Tool zur Verwaltung des Clusters, aber es ist wichtig, dieses zusätzlich abzusichern, um unerlaubte Zugriffe zu verhindern. Mithilfe des OAuth2-Proxys und Authentik kann ich sicherstellen, dass nur autorisierte Nutzer darauf zugreifen können.
Schritt-für-Schritt Konfiguration:
- Authentik einrichten: Erstelle eine OAuth2-Anwendung in Authentik und füge den OAuth2-Proxy als Client hinzu.
- OAuth2-Proxy konfigurieren: Verknüpfe den Proxy mit der Authentik-Anwendung.
- Dashboard sichern: Deaktiviere den Ingress und nutze den OAuth2-Proxy mit einer Upstreamkonfiguration.
Den Helmchart des OAuth2-Proxies kann man so konfigurieren via values.yaml:
...
config:
configFile: |-
email_domains = [ "*" ]
upstreams = [ "http://kubernetes-dashboard-kong-proxy" ]
pass_access_token = true
...
extraArgs:
provider: oidc
provider-display-name: "Authentik"
skip-provider-button: "true"
pass-authorization-header: "true"
set-authorization-header: true
oidc-issuer-url: https://<authentik-domain>/application/o/kube-apiserver/
redirect-url: https://<dashboard-domain>/oauth2/callback
#redis-connection-url: "redis://oauth2-proxy-redis-master" # if you want to use redis
session-store-type: cookie # alternative is to use redis or cookie
cookie-refresh: 119m
...
ingress:
enabled: true
className: ""
path: /
pathType: ImplementationSpecific
hosts:
- <dashboard-domain>
labels: {}
annotations:
external-dns.alpha.kubernetes.io/hostname: <dashboard-domain>. # creates a DNS entry
external-dns.alpha.kubernetes.io/target: <CNAME or A-Record?>.
tls:
- secretName: <secret name that contains https certificate>
hosts:
- <dashboard-domain>
Code-Sprache: PHP (php)
RBAC: Benutzerrollen und Berechtigungen verwalten
Zusätzlich zur Authentifizierung durch Authentik wird im Kubernetes-Cluster die Autorisierung durch RBAC (Role-Based Access Control) geregelt. RBAC ermöglicht es, spezifische Berechtigungen basierend auf Rollen zu vergeben, was besonders nützlich ist, wenn mehrere Benutzer im Cluster arbeiten oder Zugriff auf bestimmte Anwendungen benötigen.
RBAC funktioniert, indem es Rollen (Roles) definiert, die mit Berechtigungen (Permissions) verbunden sind. Diese Rollen können dann bestimmten Benutzern oder Gruppen zugewiesen werden, um festzulegen, welche Aktionen sie im Cluster ausführen dürfen. So kannst du genau steuern, welche Befugnisse jeder Benutzer hat.
Zum Beispiel habe ich für das Kubernetes-Dashboard spezifische RBAC-Rollen definiert, die sicherstellen, dass nur autorisierte Benutzer das Dashboard verwalten oder sensible Daten einsehen können. Hier ein Beispiel für eine einfache RBAC-Konfiguration für das Dashboard:
apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
namespace: kubernetes-dashboard
name: dashboard-user
rules:
- apiGroups: [""]
resources: ["pods", "services", "endpoints", "configmaps"]
verbs: ["get", "list", "watch"]
---
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
name: dashboard-user-binding
namespace: kubernetes-dashboard
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: Role
name: dashboard-user
subjects:
- kind: User
name: "<Benutzername>"
apiGroup: rbac.authorization.k8s.io
Code-Sprache: JavaScript (javascript)
In dieser Konfiguration bekommt der Benutzer die dashboard-user-Rolle zugewiesen, die ihm Zugriff auf Ressourcen wie Pods und Services im Kubernetes-Dashboard gewährt.
Auf meinem Cluster habe ich es mir einfach gemacht und die vorhandene Rolle cluster-admin verwendet. Das Vorgehen ist allerdings nur empfehlenswert, wenn die Anzahl der Administratoren sehr klein ist. Hiermit wird die Clusterrolle einer Gruppe aus authentik zugewiesen:
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1
metadata:
name: oidc-group-admin-kube-apiserver
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: cluster-admin
subjects:
- kind: Group
name: admin-kube-apiserver
Desweiteren habe ich den kube-api-server in der ansible-Konfiguration aktiviert:
kube-apiserver-arg:
- "oidc-issuer-url=https://<authentik-url/application/o/kube-apiserver/"
- "oidc-client-id=kube-apiserver"
- "oidc-username-claim=email"
- "oidc-groups-claim=groups"
Code-Sprache: JavaScript (javascript)
RBAC und Authentik
Die Authentifizierung über Authentik wird in Kombination mit RBAC noch leistungsfähiger, da du für authentifizierte Benutzer direkt Rollen definieren kannst. Das bedeutet, dass du nicht nur sicherstellst, dass Benutzer authentifiziert sind, sondern auch genau festlegen kannst, was sie im Cluster tun dürfen. So kann z.B. ein Administrator Zugriff auf alle Ressourcen haben, während ein normaler Benutzer nur lesenden Zugriff auf bestimmte Bereiche des Dashboards erhält.
Vorteile und erweiterte Möglichkeiten
Neben dem Kubernetes-Dashboard kann diese Lösung auf andere Anwendungen in deinem Cluster ausgeweitet werden. Jede Anwendung, die OAuth2 unterstützt, lässt sich so absichern. Außerdem gibt es Alternativen wie Keycloak oder Dex, die ähnliche Funktionen bieten, je nach deinen Anforderungen.
Fazit
Durch die Kombination von Authentik für die Authentifizierung und RBAC für die Autorisierung habe ich eine flexible und sichere Lösung für mein Kubernetes-Cluster implementiert. Benutzer können sich nicht nur sicher anmelden, sondern erhalten auch nur die Rechte, die sie benötigen.
Weitere Blogposts aus der k3s-Reihe
- Einführung in meinen Kubernetes-Heimcluster: Warum und Wie?
- Der Aufbau meines Kubernetes-Heimclusters: Die Wahl der Hardware
- Initialisierung meines Heim-Kubernetes-Clusters: k3s mit Ansible
- GitOps mit FluxCD für meinen Heim-Kubernetes-Cluster
- Sichere Verwaltung von Kubernetes Secrets mit Sealed Secrets
- Automatisierte DNS- und SSL-Zertifikatsverwaltung in Kubernetes
- Ingress und Load Balancer in Kubernetes: Traefik und MetalLB
- Storage, Backup und Restore in meinem Kubernetes-Cluster
- K3s: Automatisierte Updates mit Renovate
- Anwendungen in meinem k3s-Setup