Wer mehrere Kubernetes-Cluster mit unterschiedlichen Distributionen betreibt, wünscht sich ein zentrales Managementwerkzeug. Ein potenzieller Kandidat hierfür ist das Open-Source-Tool "Open Cluster Manager". Unser Workshop beschreibt, wie Sie die Software in einer Testumgebung in Betrieb nehmen und welche Rolle Placement-Regelwerke beim Verteilen von Anwendungen spielen.
Mit der zunehmenden Containerisierung von Applikationen stehen Administratoren vor dem Problem, dass sie nicht nur eine Plattform verwalten müssen, sondern mehrere. Dabei kommen in hybriden Cloudumgebungen im Zweifelsfall verschiedene Architekturen zum Einsatz. Zu Clustern mit OpenShift, Rancher oder CDK im Rechenzentrum gesellen sich Kubernetes-Cloudsetups von Amazon, Azure oder Google.
Und dann gibt es natürlich auch die Edge-Devices, die eine Miniaturversion von Kubernetes oder nur eine simple Container-Runtime wie Podman verwenden. Der große Vorteil der Containerisierung ist aber genau derjenige, dass Apps in Containern problemlos auf allen eben genannten Plattformen arbeiten. Dem Administrator fehlt dann nur noch eins: Das richtige Verwaltungstool, das mit dem Plattformmix zurechtkommt.
Unser Artikel im März-Heft [1] beschreibt, wie Sie Ansible als Tool zum Verteilen der Applikationen einsetzen können. Es gibt aber auch andere Möglichkeiten wie beispielsweise den Open Cluster Manager.
Mit der zunehmenden Containerisierung von Applikationen stehen Administratoren vor dem Problem, dass sie nicht nur eine Plattform verwalten müssen, sondern mehrere. Dabei kommen in hybriden Cloudumgebungen im Zweifelsfall verschiedene Architekturen zum Einsatz. Zu Clustern mit OpenShift, Rancher oder CDK im Rechenzentrum gesellen sich Kubernetes-Cloudsetups von Amazon, Azure oder Google.
Und dann gibt es natürlich auch die Edge-Devices, die eine Miniaturversion von Kubernetes oder nur eine simple Container-Runtime wie Podman verwenden. Der große Vorteil der Containerisierung ist aber genau derjenige, dass Apps in Containern problemlos auf allen eben genannten Plattformen arbeiten. Dem Administrator fehlt dann nur noch eins: Das richtige Verwaltungstool, das mit dem Plattformmix zurechtkommt.
Unser Artikel im März-Heft [1] beschreibt, wie Sie Ansible als Tool zum Verteilen der Applikationen einsetzen können. Es gibt aber auch andere Möglichkeiten wie beispielsweise den Open Cluster Manager.
Testumgebung mit kind
Wer Tools für das Multi-Cluster-Management evaluieren möchte, braucht dafür natürlich erst einmal eine Multi-Cluster-Umgebung. Das erfordert jede Menge Zeit und – bei cloudbasierten Clustern – auch jede Menge Geld. Test-Cluster speziell für Management- und API-Tests bekommen Anwender aber viel einfacher und günstiger. Das passende Tool dazu stammt von den Kubernetes-Machern selbst und heißt "kind" [2].
Das Werkzeug setzt dazu "nested"-Container ein. Es startet komplette Kubernetes-Cluster mit dem passenden Virtual Networking in cri-o-Containern und das Ganze innerhalb eines Podman- oder Docker-Containers. Der Basisaufbau routet dabei lediglich den API-Management-Port des Clusters zum Hostsystem durch. Mit ein paar zusätzlichen Port-Mapping-Regeln schickt kind auch Applikationsdaten in einen Anwendungs-Pod innerhalb des kind-Clusters. Allerdings sollte sich das auf Testumgebungen beschränken.
Das Praktische an kind ist, dass sich damit auf einem einzigen Host gleich mehrere Kubernetes-Cluster betreiben lassen. So können Sie mit relativ wenig Aufwand ihre Multi-Cluster-Managementtools testen.
Um kind aufzusetzen, benötigen Sie lediglich eine physische oder virtuelle Maschine mit 8 GByte RAM und vier vCPUs, auf der Podman oder Docker läuft. Die eigentliche Installation führen Sie wahlweise über die "Go"-Runtime oder einen Paketmanager aus. kind bedarf dabei gar nicht zwingend einer Linux-Umgebung – über den Windows-Paketmanager "Chocolatey" lässt es sich in Verbindung mit dem Docker-Desktop für Windows nutzen. Auf dem Mac funktioniert das via Brew. Somit läuft es ganz einfach auf Ihrem Desktop oder Notebook.
Nachdem Sie das Tool installiert haben, erstellen Sie eine Kubernetes-Testumgebung mit einem einzigen Kommando:
kind create cluster
Das Werkzeug startet nun auch in Ihrer Docker- oder Podman-Umgebung einen einzelnen Container mit einem Single-Node-Kubernetes-Setup. kind richtet dazu das passende Port-Mapping von einem zufällig gewählten Localhost-Port zur API auf dem Container-internen Port 6443 ein. Darum brauchen Sie sich aber nicht zu kümmern, denn das Tool legt in Ihrem Benutzerverzeichnis gleich eine passende "~/.kube/config"-Datei mit den Zugangsdaten an. Unmittelbar nach dem Start lässt sich der Cluster mit dem Namen "kind-kind" via "kubectl" ansprechen:
kubectl cluster-info
Ein simples kind delete cluster genügt, um den Cluster zu entfernen, samt dem Eintrag in "~/.kube/config". Um mehrere Cluster einzurichten, starten Sie kind einfach mit dem "Name"-Parameter. Da das Werkzeug für beide Cluster die Authentisierung in der kubeconfig ablegt, wählen Sie den zu verwaltenden Cluster einfach via Kontext-Switch aus:
kubectl cluster-info --context kind-test2
oder deklarieren einen Cluster als Default:
kubectl config use-context kind-test1
Für Tests mit verschiedenen Cluster-Konfigurationen können Sie auch eine Konfigurationsdatei erstellen, die die Zahl der Controller- und Worker-Nodes angibt. Für unsere Zwecke reichen Sinlge-Node-Cluster jedoch völlig aus.
Bild 1: Auf dem Hub-Cluster läuft Open Cluster Manager zusammen mit dem Placement Controller.
Aufbau von Open Cluster Manager
Das Community-Projekt "Open Cluster Manager" [3], kurz OCM, verwaltet zentral mehrere Kubernetes-Cluster. Dabei ist es OCM egal, welche Kubernetes-Distribution dabei zum Einsatz kommt. Die Architektur von OCM lehnt sich stark an der Kubernetes-Architektur selbst und dessen API an. Ein Kubernetes-Worker-Node innerhalb eines Clusters betreibt beispielsweise mit "Kubelet" den Clientdienst, den die Control-Plane des Clusters steuert. Bei OCM gibt es einen Hub-Cluster, der als Control-Plane für die angebundenen Kubernetes-Setups dient. Auf den gemanagten Clustern läuft dann das "Klusterlet" als Client.
OCM verwendet für seine Arbeit keinen eigenen Kommunikationsport, sondern klinkt sich wie andere Erweiterungen direkt in die Kubernetes-API ein. Damit das funktioniert, müssen sich Hub und gemanagte Cluster gegenseitig sehen können. Das heißt: Der Hub muss Zugriff auf den Kubernetes-API-Port der verwalteten Cluster haben – ebenso wie die verwalteten Cluster Zugriff auf die API des Hub-Clusters haben müssen. Eine hybride Umgebung mit Clustern in der Cloud und solchen innerhalb eines Rechenzentrums benötigt daher die passenden Firewall- und Portregeln für den Zugang zur API. Eine Kommunikation zwischen den einzelnen gemanagten Clustern ist jedoch nicht nötig.
Mit OCM definieren Sie Ihre Kubernetes-Applikationen als sogenannte "ManifestWorks". Diese dienen als Applikationsvorlagen, die sich über den Hub auf einem der gemanagten Cluster ausrollen und überwachen lassen. Die Verwaltung der Manifeste ist vergleichsweise simpel. Sie nehmen dazu einfach die bestehende YML-Deklaration Ihrer Applikation mit den üblich verdächtigen Ressourcen wie Deployments und PVs und packen diese mit ein paar Metadaten für das eigentliche Manifest in eine neue YML-Datei. Dann kann OCM die Applikation an den angegebenen Cluster übergeben und deren Betrieb dort überwachen.
Dabei müssen Sie nicht zwingend einen Cluster direkt für die Ausführung einer Applikation angeben. OCM verwaltet zudem Cluster-Sets mit Placement-Regeln. Somit lassen sich Applikationen einer Cluster-Gruppe zuweisen, wobei OCM dann anhand des Regelwerks entscheidet, auf welchem Cluster die Applikation letzten Endes läuft. In den vielen Optionen des Placements liegt eine der Stärken von OCM. Es lassen sich hier sehr detaillierte Regelwerke erstellen, um die Applikationen passend zu den benötigten Ressourcen oder den Betriebskosten zu verteilen.
Da OCM nur mit der "rohen" Kubernetes-API arbeitet, kann es Cluster mit unterschiedlichen Kubernetes-Distributionen verwalten. Sie müssen aber darauf achten, dass Ihre Workloads keine Distributions-spezifischen Funktionen und API-Erweiterungen nutzen, die ein Ziel-Cluster gegebenenfalls gar nicht kennt. Wer beispielsweise OpenShift-Routen deklariert, kann diese Applikation nicht auf einem Google-Cluster verwenden. Aber auch hier helfen Placement-Regeln dabei, die Manifeste korrekt zu platzieren.
OCM in Betrieb nehmen
Ein Testaufbau mit OCM und kind ist schnell erstellt. Für den Workshop nutzen wir eine RHEL-9-VM mit vier vCPUs und 8 GByte RAM. Ein EL-8/9-Klon oder Fedora funktionieren gleichermaßen. Auf dem System installieren Sie zunächst Podman und die Go-Umgebung:
dnf install podman golang
Falls Sie Applikationen aus den Quelldateien übersetzen wollen, richten Sie zudem die nötigen Entwicklertools ein:
dnf group install "Development Tools"
Installieren Sie den Kubernetes-Client "kubectl". Je nach Distribution bekommen Sie diesen über das OpenShift-Client-Paket (RHEL) oder direkt von der Kubernetes Seite:
Von dort erhalten Sie auch gleich das Binärpaket von kind. Zum Zeitpunkt dieses Artikels liegt das Tool in der Version 0.17.0 vor. Möglicherweise gibt es bereits eine neuere Version, prüfen Sie also vor der Installation die Projektseite. Alternativ installieren Sie kind aus den Quelldateien des Git-Repositories auf [4], dann arbeiten Sie auf jeden Fall mit der aktuellen Version:
Machen Sie kind ausführbar und platzieren Sie es in einem Verzeichnis im "Path".
chmod +x ./kind
sudo mv ./kind /usr/bin/kind
Um einen besseren Einblick in Ihre kind-Cluster zu erhalten, empfehlen wir an dieser Stelle, das Tool K9s als TUI (zeichenorientierte Benutzerschnittstelle) zu verwenden. Erstellen Sie nun zwei Testcluster:
kind create cluster --name hub
kind create cluster --name one
Bild 2: Auf dem Hub generiert OCM pro gemanagtem Cluster einen gleichnamigen Workspace. Darin sammelt das Managementtool die "Manifeste".
Spielen Sie dann das OCM-Admin-Tool "clusteradm" auf. Auch hier gibt es ein fertiges Binary, das Sie nur noch in Ihren Pfad kopieren müssen:
In unserem Test gab es Probleme mit dem Context-Switch und clusteradm. Um das zu umgehen, wechseln Sie vor Operationen mit einem Cluster jeweils den Kontext:
kubectl config use-context kind-hub
Das OCM-Admin-Tool richtet dann das OCM-Setup auf ihrem ersten kind-Cluster mit lediglich einer Zeile ein:
clusteradm init --wait --context kind-hub
Das Werkzeug erstellt nun zwei Namespaces namens "open-cluster-management" und "open-cluster-management-hub". Letzterer enthält die Managementkomponenten wie Placement- und den Registration-Controller.
Am Ende der Hub-Initialisierung gibt clusteradm die Kommandozeile aus, mit der Sie Cluster am Hub anmelden. Speichern Sie diese Zeile unbedingt an einem sicheren Ort, denn sie enthält das nötige Registrierungstoken. Schalten Sie nun also den Kontext auf den zu verwaltenden Cluster um:
kubectl config use-context kind-one
Führen Sie dann die angegebene Registrierungszeile mit einer wichtigen Änderung aus. Denn damit die Registrierung eines kind-Clusters funktioniert, müssen Sie clusteradm dazu zwingen, den lokalen API-Endpoint zu nutzen:
clusteradm join --hub-token <Token> --cluster-name one --context kind-one --force-internal-endpoint-lookup
Clusteradm installiert nun das Clusterlet auf dem zu verwaltenden Knoten und schickt im Anschluss die Registrierungsanfrage an den Management-Hub.
Sobald diese dort eintrifft, müssen Sie das angeforderte Zertifikat bestätigen.Prüfen Sie auf dem Hub-Knoten, ob der Certificate Signing Request (CSR) vorliegt:
kubectl get csr --context kind-hub
Erscheint der Signing Request in der Liste, fügen Sie den Cluster hinzu:
kubectl config use-context kind-hub clusteradm accept --clusters one --context kind-hub
Wie erwähnt sollte eigentlich die zweite Zeile allein genügen. Im Test funktionierte der Switch "--context" jedoch nicht immer zuverlässig mit dem clusteradm-Kommando. Bei einem Erfolg sollte der Cluster "One" Teil des Managementverbunds sein und in der Übersicht auftauchen:
kubectl get managedcluster --context kind-hub
Die Ausgabe sollte dann den Cluster "one" in den Spalten "Accepted", "Joined" und "Available" jeweils als "True" auflisten.
Bild 3: Auf dem gemanagten Cluster "One" läuft ein Nginx-Demo-Rollout, wie es über das Manifest vom Hub-Cluster bestellt wurde. Der OCM-Agent (clusterlet) ist dafür zuständig, die Anforderungen von OCM lokal umzusetzen.
Arbeit sinnvoll verteilen
Solange noch keine Placement Rules existieren, können Sie schon einmal simple Workloads statisch über OCM auf die gemanagten Knoten verteilen. Nehmen Sie dazu eine bestehendes YML-File, das eine Applikation beschreibt und das sich einfach über kubectl apply -f auf einem Cluster ausrollen lässt.
Wir verwenden für unseren Workshop ein schlichtes Nginx-Template. Mithilfe des Clusteradm-Tools lassen sich bestehende Definitionsdateien einfach an einen Cluster deligieren:
clusteradm create work nginx1 -f nginx.yml --clusters one --context kind-hub
Der OCM-Hub sendet dann die Anforderung an den Cluster "One", der im Anschluss alle im YML aufgelisteten Ressourcen generiert und startet. Über den Hub sehen Sie den Status ihrer Applikation ein:
clusteradm get works --cluster one
Auch das reguläre kubectl-Tool zeigt die Loads an, zum Beispiel mit:
kubectl get manifestwork -A --context kind-hub
Alternativ zu clusteradm generiert kubectl Works und rollt sie aus. Sie müssen dazu nur Ihre bestehende YML-Datei etwas erweitern. Üblicherweise beginnt die Deklaration in etwa so:
apiVersion: apps/v1
kind: Deployment
metadata:
namespace: default
...
Als Work sieht das Ganze nur ein wenig anders aus:
apiVersion: work.open-cluster-management.io/v1
kind: ManifestWork
metadata:
namespace: one
name: nginx1
spec:
workload:
manifests:
- apiVersion: v1
kind: Deployment
metadata:
namespace: default
...
Beachten Sie, dass in diesem Beispiel die Zuweisung zum Cluster "One" statisch im Manifest steht.
Wenn Sie mehr als einen Cluster mit OCM verwalten, erstellen sie dann zunächst Placement-Regelwerke als "kind: Placement" und verteilen dann die Workloads gemäß der Regelwerke auf die verwalteten Cluster:
clusteradm create work nginx1 -f nginx1.yml --placement <Namespace>/<Name des Placements-Ruleset>
Wie Placements aktuell funktionieren, dokumentiert die Webseite des Projekts sehr ausführlich unter [5]. Die vielen Optionen im Detail zu beschreiben, würde den Umfang des Artikels jedoch sprengen.
Alternative Flotta
Ein ähnliches Ziel wie OCM verfolgt das Open-Source-Projekt Flotta [6]. Auch hier steht ein Kubernetes-Cluster als zentrale Managementplattform im Zentrum. Flotta verwaltet jedoch keine anderen Kubernetes-Cluster, sondern Edge-Devices ohne Kubernetes. Auf den Zielsystemen läuft lediglich Podman als Container-Runtime. Anders als OCM nutzt Flotta nicht die bestehende Kubernetes-API mit eigenen Erweiterungen, sondern braucht einen eigenen Port für seine Management-API. Edge-Devices müssen Zugang zum Flotta-Port auf dem Management-Cluster erhalten – umgekehrt kommt Flotta ohne dauerhaften Zugang zu den Devices aus. Das Werkzeug setzt gar nicht voraus, dass die Egde-Devices dauerhaft mit dem Flotta-Dienst in Verbindung stehen.Auf den verwalteten Knoten läuft dann der Flotta-Agent, der die zugewiesenen Workloads via Podman und Systemd auf dem jeweiligen Edge-Device ausführt. Der Agent prüft regelmäßig – falls es die Netzwerkverbindung des Edge-Devices erlaubt –, ob der Flotta-Server Aufträge parat hat. Dabei kann das Tool natürlich nicht jede beliebige Kubernetes-Applikation einfach auf ein Edge-Device delegieren. Der Administrator muss zuvor sicherstellen, dass die gewünschten Workloads mit Podman arbeiten.Leider gibt es in letzter Zeit wenig Neues beim Projekt. Der Hauptsponsor Red Hat legt bei Edge-Devices aktuell mehr Gewicht auf MicroShift und hat daher eine Reihe von Flotta-Entwicklern zu den Teams von MicroShift oder OCM umgesiedelt. Ganz abschreiben sollten wir Flotta aber noch nicht. Es besteht ein reges Interesse an Edge-Implementierungen ohne Kubernetes und vielleicht finden sich weitere Community-Entwickler, um das interessante Projekt fortzuführen. Wer es praktisch ausprobieren möchte, braucht ein simples Kubernetes-Setup, das den Flotta-Operator und -Dienst betreibt, sowie eine Fedora-36-VM als simuliertes Edge-Device.
Fazit
OCM liefert den passenden Unterbau für ein Multi-Cluster-Management für Kubernetes. Neben den integrierten Funktionen für Management und Placement bringt das Tool zudem einen Add-On-Manager mit. Andere Projekte erweitern somit die Funktionalität, doch eine GUI für OCM findet sich nur in kommerziellen Implementierungen. Mit zunehmender Adaption in hybriden Umgebungen ist es aber wohl nur eine Frage der Zeit, bis freie Kubernetes-UIs auch OCM grafisch darstellen können.