Einsatz von Keycloak auf Kubernetes mit einer Beispielanwendung auf CODE-DE

Keycloak ist eine große Open-Source Identitätsmanagement-Suite, die eine breite Palette von identitätsbezogenen Anwendungsfällen handhaben kann.

Mit Keycloak ist es einfach, eine robuste Autentifizierungs-/Autorisierungslösung für Ihre Anwendungen zu implementieren. Nach der anfänglichen Bereitstellung können Sie es leicht konfigurieren, um neue identitätsbezogene Anforderungen zu erfüllen, z. B. Multi-Faktor-Authentifizierung, Föderation zu Social-Providern, benutzerdefinierte Passwortrichtlinien und viele andere.

Was wir tun werden

  • Keycloak auf einem Kubernetes-Cluster bereitstellen

  • Keycloak konfigurieren: einen Realm, einen Client und einen Benutzer erstellen

  • Einsatz einer Python-Webanwendung mit Keycloak für die Authentifizierung

Voraussetzungen

Nr. 1 Konto

Sie benötigen einen CODE-DE Hosting-Konto mit Horizon-Schnittstelle https://cloud.fra1-1.cloudferro.com/auth/login/?next=/.

Nr. 2 Ein laufender Kubernetes-Cluster und kubectl aktiviert

Ein Kubernetes-Cluster, um eines zu erstellen, siehe: Erstellen eines Kubernetes-Clusters mit CODE-DE OpenStack Magnum. To activate kubectl, see Zugriff auf Kubernetes-Cluster nach der Bereitstellung mit Kubectl auf CODE-DE OpenStack Magnum.

Nr. 3 Grundkenntnisse in Python und der pip-Paketverwaltung

Grundlegende Kenntnisse von Python und der pip-Paketverwaltung werden vorausgesetzt. Python 3 und pip sollten auf Ihrem lokalen Rechner bereits installiert und verfügbar sein.

Nr. 4 Vertrautheit mit der OpenID Connect (OIDC) Terminologie

Eine gewisse Vertrautheit mit der Terminologie von OpenID Connect (OIDC) ist erforderlich. Einige wichtige Begriffe werden in diesem Artikel kurz erklärt.

Schritt 1 Bereitstellung von Keycloak auf Kubernetes

Erstellen wir zunächst einen eigenen Kubernetes-Namensraum für Keycloak. Dies ist optional, aber gute Praxis:

kubectl create namespace keycloak

Dann setzen Sie Keycloak in diesem Namespace ein:

kubectl create -f https://raw.githubusercontent.com/keycloak/keycloak-quickstarts/latest/kubernetes-examples/keycloak.yaml -n keycloak

Keycloak wird standardmäßig als Kubernetes-Dienst vom Typ LoadBalancer auf Port 8080 bereitgestellt. Sie müssen die öffentliche IP-Adresse des Dienstes mit folgendem Befehl herausfinden (beachten Sie, dass es ein paar Minuten dauern kann, bis sie eingetragen ist):

kubectl get services -n keycloak
NAME          TYPE           CLUSTER-IP      EXTERNAL-IP      PORT(S)          AGE
keycloak      LoadBalancer   10.254.8.94     64.225.128.216   8080:31228/TCP   23h

Bemerkung

In unserem Fall lautet die externe IP-Adresse 64.225.128.216, die wir in diesem Artikel verwenden werden. Ersetzen Sie sie durch Ihre eigene IP-Adresse.

Geben Sie also http://64.225.128.216:8080/ in den Browser ein, um auf Keycloak zuzugreifen:

../_images/image2023-4-4_13-37-48.png

Klicken Sie dann auf Administrationskonsole und Sie werden zum Anmeldebildschirm weitergeleitet, wo Sie sich als Administrator anmelden können (Login/Passwort admin/admin )

../_images/image2023-4-4_13-28-40.png

Dies ist eine Vollbildansicht des Keycloak-Fensters:

../_images/keycloack_full_screen.png

Schritt 2 Keycloak-Realm erstellen

In der Keycloak-Terminologie ist ein Realm ein dedizierter Bereich für die Verwaltung einer isolierten Untergruppe von Benutzern, Rollen und anderen zugehörigen Entitäten. Keycloak hat zunächst einen Master-Realm, der für die Verwaltung von Keycloak selbst verwendet wird.

Unser nächster Schritt besteht darin, unseren eigenen Realm zu erstellen und in seinem Kontext zu arbeiten. Um ihn zu erstellen, klicken Sie zuerst auf das Feld Master in der oberen linken Ecke und dann auf Realm erstellen.

../_images/image2023-6-14_15-24-46.png

Wir geben nur den Namen des Bereichs myrealm ein und lassen den Rest unverändert:

../_images/image2023-6-14_15-26-51.png

Wenn der Bereich erstellt (und ausgewählt) wurde, arbeiten wir in diesem Bereich:

../_images/image2023-6-14_15-29-22.png

In der linken oberen Ecke steht nun anstelle von master der Name des ausgewählten Realms, myrealm.

Schritt 3 Keycloak-Client erstellen und konfigurieren

Clients sind Entitäten in Keycloak, die Keycloak auffordern können, Benutzer zu authentifizieren. In der Praxis kann man sie als Repräsentanten einzelner Anwendungen betrachten, die die von Keycloak verwaltete Authentifizierung/Autorisierung nutzen wollen.

Innerhalb des myrealm-Bereichs werden wir nun einen Client myapp erstellen, der die Webanwendung repräsentiert, die wir in einem der nächsten Schritte erstellen werden. Um einen solchen Client zu erstellen, klicken Sie auf das Panel Clients im linken Menü und dann auf die Schaltfläche Create Client.

Sie gelangen zu einem Assistenten, der aus 3 Schritten besteht. Im ersten Schritt geben wir nur die ID des Clients ein (in unserem Fall myapp) und lassen die anderen Einstellungen unverändert:

../_images/image2023-6-14_15-40-56.png

Auf dem nächsten Bildschirm müssen Sie einige wichtige Einstellungen vornehmen, die sich auf die Authentifizierungs-/Autorisierungsanforderungen Ihrer spezifischen Anwendung beziehen.

../_images/create_client_with_authentication.png

Welche Optionen Sie wählen, hängt von Ihrem jeweiligen Szenario ab:

Szenario 1 Traditionelle Serveranwendungen

Für die Zwecke dieses Artikels und unserer Demo-Anwendung verwenden wir eine traditionelle Client-Server-Anwendung. In diesem Fall müssen wir den Schalter „Client-Authentifizierung“ aktivieren.

Szenario 2 SPA

Bei einseitigen Anwendungen können Sie die Standardeinstellung beibehalten, bei der der Schalter „Client-Authentifizierung“ deaktiviert ist.

Für unsere Demo-Anwendung benötigen wir eine Authentifizierung über das Geheimnis, daher müssen Sie die Option Client-Authentifizierung aktivieren. Sobald diese Option aktiviert ist, können wir den Wert von secret später in Schritt 5 abrufen.

Der letzte Schritt des Assistenten beinhaltet die Einstellung einiger Schlüsselkoordinaten unserer Client-Anwendung. Die von uns geänderten Werte sind:

../_images/image2023-6-14_16-8-44.png
root URL

In unserem Fall wollen wir die App lokal bereitstellen, also richten wir das Stammverzeichnis als http://localhost ein. Sie müssen dies ändern, wenn Ihre Anwendung als öffentlicher Dienst bereitgestellt werden soll.

Gültige Redirect-URIs

Diese Einstellung stellt eine Route in unserer Anwendung dar, zu der ein Benutzer nach einem erfolgreichen Login von Keycloak umgeleitet wird. In unserem Fall lassen wir diese Einstellung sehr freizügig mit einem „*“, was eine Umleitung zu jedem Pfad in unserer Anwendung erlaubt. Für die Produktion sollten Sie dies expliziter machen und eine eigene Route, z.B. /callback, für diesen Zweck verwenden.

Web-Origins

Diese Einstellung legt die Hosts fest, die Anfragen an Keycloak senden können. Anfragen von anderen Hosts werden die Cross-Origin-Prüfung nicht bestehen und werden abgelehnt. Auch hier sind wir sehr freizügig, indem wir ein „*“ setzen. Ähnlich wie oben sollten Sie diese Einstellung für die Produktion ändern und nur auf vertrauenswürdige Quellen beschränken.

Nachdem Sie auf Speichern geklickt haben, wird Ihr Mandant erstellt. Sie können dann die zuvor ausgewählten Einstellungen des erstellten Clients ändern und neue, spezifischere Einstellungen hinzufügen. Es gibt eine Vielzahl von Möglichkeiten für weitere Anpassungen je nach den Besonderheiten Ihrer Anwendung, was jedoch den Rahmen dieses Artikels sprengen würde.

Schritt 4 Erstellen eines Benutzers in Keycloak

Nachdem wir den Client erstellt haben, werden wir unseren ersten Benutzer in Keycloak erstellen. Klicken Sie dazu auf die Registerkarte Benutzer auf der linken Seite und dann auf Neuen Benutzer erstellen:

Wir werden wieder sehr restriktiv sein und nur test als Benutzernamen wählen, während wir die anderen Optionen unberührt lassen:

../_images/image2023-6-14_16-41-7.png

Als Nächstes richten wir die Kennwortdaten für den neu angelegten Benutzer ein. Wählen Sie die Registerkarte Zugangsdaten und dann Kennwort festlegen, geben Sie das Kennwort mit Bestätigung in das Formular ein und klicken Sie auf Speichern:

../_images/image2023-6-15_8-43-7.png

Schritt 5 Abrufen des Client-Geheimnisses von Keycloak

Sobald wir Keycloak eingerichtet haben, müssen wir das Client-Geheimnis extrahieren, damit Keycloak Vertrauen zu unserer Anwendung aufbauen kann.

Das client_secret kann extrahiert werden, indem man in myrealm realm geht, myapp als Client auswählt und dann das Client-Geheimnis mit der folgenden Befehlskette nimmt:

Clients –> Client detail –> Credentials

Sobald Sie sich auf der Registerkarte Zertifikate befinden, wird das Geheimnis über das Feld Client Secret zugänglich:

../_images/image2023-6-26_11-27-0.png

Aus Gründen des Schutzes der Privatsphäre ist er im Screenshot oben gelb dargestellt. In Ihrem Fall sollten Sie sich den Wert notieren, da Sie ihn im nächsten Schritt in den Anwendungscode einfügen müssen.

Schritt 6 Erstellen einer Flask-Webanwendung mit Keycloak-Authentifizierung

Zur Erstellung der App werden wir Flask verwenden, ein reduziertes, auf Python basierendes Web-Framework. Keycloak unterstützt auch eine breite Palette anderer Technologien. Wir werden die Flask-OIDC-Bibliothek verwenden, die Flask um die Fähigkeit erweitert, OpenID Connect-Authentifizierungs-/Autorisierungsszenarien auszuführen.

Als Voraussetzung müssen Sie die folgenden pip-Pakete installieren, um die Abhängigkeitskette abzudecken. Führen Sie die Befehle am besten von einer bereits vorinstallierten virtuellen Python-Umgebung aus:

pip install Werkzeug==2.3.8
pip install Flask==2.0.1
pip install wheel==0.40.0
pip install flask-oidc==1.4.0
pip install itsdangerous==2.0.1

Dann müssen Sie 2 Dateien erstellen: app.py und keycloak.json. Sie müssen die folgenden Änderungen in diesen Dateien vornehmen:

Ersetzen Sie die IP-Adresses

Ersetzen Sie in keycloak.json 64.225.128.216 durch Ihre eigene externe IP aus Schritt 1.

Ersetzen Sie client_secret

Ersetzen Sie wiederum in keycloak.json den Wert der Variable client_secret durch das Geheimnis aus Schritt 5.

Ersetzen von client_secret

Ersetzen Sie in der Datei app.py den Wert von SECRET_KEY durch das gleiche Geheimnis aus Schritt 5.

Erstellen Sie eine neue Datei namens app.py und fügen Sie den folgenden Inhalt ein:

from flask import Flask, g
from flask_oidc import OpenIDConnect
import json

app = Flask(__name__)

app.config.update(
        SECRET_KEY='XXXXXX',
        OIDC_CLIENT_SECRETS='keycloak.json',
        OIDC_INTROSPECTION_AUTH_METHOD='client_secret_post',
        OIDC_TOKEN_TYPE_HINT='access_token',
        OIDC_SCOPES=['openid','email','profile'],
        OIDC_OPENID_REALM='myrealm'
    )

oidc = OpenIDConnect(app)

@app.route('/')
def index():
    if oidc.user_loggedin:
        info = oidc.user_getinfo(["preferred_username", "email", "sub"])
        return 'Welcome %s' % info.get("preferred_username")
    else:
        return '<h1>Not logged in</h1>'

@app.route('/login')
@oidc.require_login
def login():
    token = oidc.get_access_token()
    info = oidc.user_getinfo(["preferred_username", "email", "sub"])
    username = info.get("preferred_username")
    return "Token: " + token + "<br/><br/>  Username: " + username

@app.route('/logout')
def logout():
    oidc.logout()
    return '<h2>Hi, you have been logged out! <a href="/">Return</a></h2>'

Der Anwendungscode lädt die Flask-Anwendung und stellt die für flask_oidc erforderlichen Konfigurationen bereit. Wir müssen die Konfiguration der

  • name of our realm, the

  • client secret_key and the

  • additional settings that reflect our specific sample flow.

Außerdem verweist diese Konfiguration auf eine weitere Konfigurationsdatei, keycloak.json, die weitere Einstellungen unseres Keycloak-Realms wiedergibt. Insbesondere finden Sie darin die Client-ID und das Geheimnis sowie die Endpunkte, an denen Keycloak weitere Informationen über die Realm-Einstellungen zur Verfügung stellt.

Create the required file keycloak.json, in the same working folder as the app.py file:

{
"web": {
    "client_id": "myapp",
    "client_secret": "XXXXXX",
    "auth_uri": "http://64.225.128.216:8080/realms/myrealm/protocol/openid-connect/auth",
    "token_uri": "http://64.225.128.216:8080/realms/myrealm/protocol/openid-connect/token",
    "issuer": "http://64.225.128.216:8080/realms/myrealm",
    "userinfo_uri": "http://64.225.128.216:8080/realms/myrealm/protocol/openid-connect/userinfo",
    "token_introspection_uri": "http://64.225.128.216:8080/realms/myrealm/protocol/openid-connect/token/introspect",
    "redirect_uris": [
      "http://localhost:5000/*"
    ]
  }
}

Beachten Sie, dass app.py 3 Routen erstellt:

/

In this route, a page is served that provides the name of a logged in user. Alternatively, if the user is not logged in yet, it prompts to do so.

/login

This route redirects the user to the Keycloak login page and upon successful authentication provides user name and token

/logout

Entering this route logs the user out.

Schritt 7 Testen Sie die Anwendung

Um die Anwendung zu testen, führen Sie den folgenden Befehl in dem Arbeitsverzeichnis aus, in dem sich die Datei app.py befindet:

flask run

Das ist das Ergebnis in einem CLI-Fenster:

../_images/flask_run.png

Wir wissen jetzt, dass auf dem localhost ein Flask-Server auf Port 5000 läuft. Geben Sie localhost:5000 in die Adressleiste des Browsers ein, und es wird die Website angezeigt, die über die Basisroute bedient wird: / . Wir haben unseren Benutzer noch nicht angemeldet, daher die entsprechende Meldung:

../_images/image2023-6-26_11-54-29.png

Der nächste Schritt ist die Eingabe der Route /login. Geben Sie localhost:5000/login in die Adresszeile des Browsers ein. Dadurch werden Sie zu Keycloak weitergeleitet und aufgefordert, sich bei myapp anzumelden:

../_images/image2023-6-26_12-0-35.png

Geben Sie zur Authentifizierung den Benutzernamen des in Schritt 3 erstellten Benutzers (Benutzername: test) und das Kennwort ein, das Sie zur Erstellung dieses Benutzers verwendet haben. Bei den Standardeinstellungen werden Sie möglicherweise aufgefordert, das Passwort nach der ersten Anmeldung zu ändern, fahren Sie dann einfach entsprechend fort. Nach der Anmeldung werden unser Benutzername und unser Token angezeigt (aus Sicherheitsgründen sind Teile des Tokens gelb gefärbt):

../_images/image2023-6-26_12-36-24.png

Die letzte zu testende Route ist /logout . Wenn Sie localhost:5000/logout in den Browser eingeben, sehen Sie den unten stehenden Bildschirm. Die Eingabe dieser Route ruft die Methode flask-oidc auf, die den Benutzer abmeldet und auch das Sitzungs-Cookie löscht.

../_images/image2023-6-26_12-42-24.png