GitOps mit FluxCD für meinen Heim-Kubernetes-Cluster

Hallo zusammen! In unseren bisherigen Beiträgen haben wir die Hardware-Auswahl und die Installation von k3s für unseren Heim-Kubernetes-Cluster besprochen. Heute tauchen wir in die Welt von GitOps ein und setzen FluxCD ein, um eine dynamische, effiziente und automatisierte Cluster-Verwaltung zu erreichen.

Was ist GitOps?

GitOps ist eine Methode zur Infrastrukturverwaltung, die Git als Single Source of Truth nutzt und automatisierte Prozesse verwendet, um sicherzustellen, dass der Zustand unseres Clusters dem in unserem Git-Repository gespeicherten Konfigurationscode entspricht. Dieser Ansatz bringt Entwicklungspraktiken wie Versionierung, Code-Review und Continuous Integration/Deployment in die Welt der Infrastrukturverwaltung.

Warum FluxCD?

FluxCD ist eines der führenden Tools, das GitOps-Prinzipien auf Kubernetes anwendet. Es überwacht Git-Repositories und stellt sicher, dass der Zustand im Cluster mit dem im Repository definierten Zustand übereinstimmt. Es ist nicht das einzige Tool dieser Art — eine Alternative ist ArgoCD, das ähnliche Funktionen bietet, jedoch einige Unterschiede in der Architektur und im Workflow aufweist. Ich habe mich für FluxCD entschieden, weil es besonders gut mit der Kubernetes-API zusammenarbeitet und eine starke Community und Unterstützung bietet.

Installation von FluxCD

Die Installation von FluxCD in unserem k3s-Cluster nutzt ein GitHub-Repository zur Konfigurationsverwaltung. Hier sind die grundlegenden Schritte:

  1. Installation des FluxCD CLI-Tools: curl -s https://fluxcd.io/install.sh | sudo bash (andere Möglichkeiten zur Installation gibt es in der Dokumentation)
  2. Voraussetzungen prüfen: flux check --pre zeigt, ob alle Voraussetzungen erfüllt sind
  3. Initialisierung von FluxCD im Cluster:
    flux bootstrap github --owner=<github-user> --repository=<repo-name> --branch=main --path=./clusters/my-cluster --personal

Dieses Kommando setzt FluxCD so auf, dass es Änderungen in einem spezifischen Pfad meines GitHub-Repositories überwacht und auf den Cluster anwendet.

Erklärung des flux bootstrap Befehls

Der flux bootstrap Befehl ist ein zentraler Bestandteil der Einrichtung von FluxCD und wird genutzt, um FluxCD automatisch in einem Kubernetes-Cluster zu installieren und es mit einem Git-Repository zu verbinden. Dieser Befehl bereitet alles vor, was für die Verwaltung des Clusters durch GitOps erforderlich ist. Hier sind die wichtigsten Optionen erklärt:

  • --owner=<github-user>: Der Benutzername oder die Organisation in GitHub, der bzw. die das Repository besitzt. Dies ist notwendig, damit FluxCD die Berechtigung hat, Änderungen zu pushen und PRs zu erstellen.
  • --repository=<repo-name>: Der Name des GitHub-Repositories, das für die Speicherung der Kubernetes-Konfigurationen verwendet wird.
  • --branch=main: Der Branch im Repository, den FluxCD für die Konfigurationsdateien verwenden wird. Standardmäßig ist dies oft main.
  • --path=./clusters/my-cluster: Der Pfad im Repository, unter dem FluxCD die Konfigurationsdateien ablegen und verwalten wird. Dies ermöglicht es dir, mehrere Cluster-Konfigurationen in einem einzigen Repository zu organisieren.
  • --personal: Eine Option, die angibt, dass das verwendete GitHub-Repository ein persönliches und kein Organisations-Repository ist.

Diese Optionen ermöglichen eine flexible und sichere Methode zur Integration von FluxCD in deinen Cluster und dein Source-Control-System, wodurch die Prinzipien von GitOps effektiv umgesetzt werden können.

Schlüsselkonzepte von FluxCD

Beim Arbeiten mit FluxCD gibt es einige wichtige “Vokabeln” oder Konzepte, die man verstehen sollte:

  • Helm Charts: Vorlagen, die beschreiben, wie eine Anwendung oder ein Dienst in Kubernetes bereitgestellt wird.
  • Helm Releases: Instanzen von Helm Charts, die im Cluster bereitgestellt sind.
  • Kustomizations: Anpassungen von Kubernetes-Ressourcen, die über die Basiskonfigurationen hinausgehen.
  • Repositories: Orte, an denen unsere Konfigurationsdateien und -skripte gespeichert sind.

Ordnerstruktur für FluxCD

Eine gut organisierte Ordnerstruktur ist entscheidend für die Verwaltung von FluxCD-Konfigurationen:

/clustername/
  /apps/
    /<appname>/
      - helmrelease.yaml
      - sealed-secret.yaml
  /bootstrap/
    /namespace/
    /helmcharts/
    /kustomizations/Code-Sprache: JavaScript (javascript)

Erläuterungen zur Struktur:

  • /apps/: Dieser Ordner enthält Unterordner für jede Anwendung (<appname>), die im Cluster läuft. Jeder Anwendungsordner würde dann die HelmRelease Konfigurationsdateien enthalten, die spezifisch für diese Anwendung sind. Außerdem können hier weitere Konfigurationen oder Secrets bereitgestellt werden.
  • /bootstrap/: Dieser Ordner enthält wichtige Ressourcen, die zur Initialisierung des Clusters erforderlich sind:
    • /namespace/: Hier werden Dateien gespeichert, die spezifische Namespaces im Cluster definieren.
    • /helmcharts/: In diesem Ordner werden die Helm Charts gespeichert, die im Cluster verwendet werden.
    • /kustomizations/: Dieser Ordner enthält Kustomizations, die zum Anpassen der Kubernetes-Ressourcen vor ihrer Anwendung im Cluster verwendet werden.

Diese Struktur hilft dabei, deine Cluster-Konfigurationen organisiert und leicht zugänglich zu halten, und unterstützt die saubere Trennung von Infrastruktur-Setup und Anwendungs-Deployment.

Beispiel: Deployment von Podinfo

Lassen wir uns nun ansehen, wie die Anwendung “Podinfo” deployed werden kann. Dazu benötigen wir einen Namespace, müssen ein Helmrepository konfigurieren sowie Kustomization und die Appkonfiguration selbst im Ordner /apps/podinfo/ anlegen:

Namespace

apiVersion: v1
kind: Namespace
metadata:
  name: podinfo
Code-Sprache: YAML (yaml)

Helmrepository

apiVersion: source.toolkit.fluxcd.io/v1beta2
kind: HelmRepository
metadata:
  name: podinfo
  namespace: default
spec:
  interval: 15m
  url: https://stefanprodan.github.io/podinfo
Code-Sprache: YAML (yaml)

Kustomization

apiVersion: source.toolkit.fluxcd.io/v1beta2
kind: HelmRepository
metadata:
  name: podinfo
  namespace: default
spec:
  interval: 15m
  url: https://stefanprodan.github.io/podinfo
Code-Sprache: YAML (yaml)

HelmRelease

apiVersion: helm.toolkit.fluxcd.io/v2beta1
kind: HelmRelease
metadata:
  name: podinfo
  namespace: podinfo
spec:
  chart:
    spec:
      chart: podinfo
      version: 6.x
      sourceRef:
        kind: HelmRepository
        name: podinfo
        namespace: default
  interval: 15m
  timeout: 5m
  releaseName: podinfo
  valuesFrom:
  - kind: ConfigMap
    name: podinfo-helm-chart-value-overrides
    valuesKey: values.yaml # This is the default, but best to be explicit for clarity
Code-Sprache: YAML (yaml)

ConfigMap für values.yaml

Im HelmRelease werden üblicherweise auch die Konfigurationswerte für die jeweilige Anwendung mitgegeben. Die möglichen Werte ergeben sich aus der Datei values.yaml, die in einem Helmchart die Standardwerte enthält. Entweder werden die Werte im Helmrelease direkt aufgeschrieben oder man verweist auf eine Configmap, die die Datei values.yaml enthält:

apiVersion: v1
kind: ConfigMap
metadata:
  creationTimestamp: null
  name: podinfo-helm-chart-value-overrides
  namespace: podinfo
data:
  values.yaml: |-
    # Default values for podinfo.

    replicaCount: 1
    logLevel: info
    host: #0.0.0.0
    backend: #http://backend-podinfo:9898/echo
    backends: []

    image:
      repository: ghcr.io/stefanprodan/podinfo
      tag: 6.0.3
      pullPolicy: IfNotPresent

    ui:
      color: "#34577c"
Code-Sprache: YAML (yaml)

Persönlich schreibe ich die Werte lieber direkt in das HelmRelease-File, damit FluxCD die Änderungen an den Werten nach einem Commit schneller deployed. Sonst wartet FluxCD bis zu einer Stunde, um auch andere Dateien eines Deployments zu aktualisieren.

Für mich hat es sich bewährt, die alle default values eines Helmcharts zu verwenden. Damit wird verhindert, dass Änderungen am Helmchart unbemerkt passieren oder sich wichtige Standardeinstellungen ändern. Ausnahmen hiervon sind Versionen oder Tags der Dockerimages. Das würde die Nutzung von Renovate konterkarieren.

Automatisiertes Update von HelmCharts mit Renovate

Um sicherzustellen, dass die von mir verwendeten Helmcharts und deren Abhängigkeiten immer auf dem neuesten Stand sind, setze ich auf Renovate, einen automatisierten Update-Dienst, den ich in meinem GitHub-Repository integriert habe. Renovate überprüft regelmäßig, ob neue Versionen der Helmcharts oder anderer Abhängigkeiten verfügbar sind, und erstellt automatisch Pull Requests, um diese Updates in mein Repository zu integrieren. Dies trägt dazu bei, dass mein Cluster mit aktuellen und sicheren Softwareversionen betrieben wird, und reduziert das Risiko von Sicherheitslücken, die durch veraltete Komponenten entstehen könnten.

Fazit und Ausblick

Mit der erfolgreichen Einrichtung von FluxCD auf unserem Kubernetes-Cluster haben wir einen soliden Grundstein für eine zuverlässige und automatisierte Cluster-Verwaltung gelegt. Dieses Setup ermöglicht es uns, Änderungen präzise und effizient zu steuern, während wir die Best Practices von GitOps nutzen.

Was erwartet euch in den kommenden Posts?

Der Aufbau eines robusten und sicheren Kubernetes-Clusters endet nicht mit der Installation von FluxCD. In den nächsten Blogposts werden wir uns mit einer Reihe von fortgeschrittenen Themen befassen, die essenziell sind, um den Cluster produktionsreif zu machen:

  • Sealed Secrets: Zum sicheren Umgang mit geheimen Daten im Cluster.
  • DNS und Zertifikate: Für die zuverlässige und sichere Erreichbarkeit unserer Services.
  • Ingress und Load Balancers: Zur Steuerung des eingehenden Netzwerkverkehrs und zur Optimierung der Lastverteilung.
  • Authentication: Um den Zugang zu unseren Diensten sicher und kontrolliert zu gestalten.
  • Storage Lösungen: Für die persistente Speicherung unserer Daten.
  • Backup & Restore: Um eine hohe Datenverfügbarkeit und Wiederherstellbarkeit im Notfall sicherzustellen.
  • Installation weiterer Anwendungen: Anwendungen, die sich nur mit ein paar Tricks und Kniffen installieren lassen.

Jeder dieser Aspekte ist entscheidend für die Aufrechterhaltung eines effizienten, sicheren und skalierbaren Kubernetes-Clusters. Ich freue mich darauf, diese Themen ausführlich zu behandeln und praktische Tipps und Anleitungen zu bieten, die euch helfen, eure eigenen Kubernetes-Installationen zu optimieren.

Bleibt dran, um mehr über die spannende Welt von Kubernetes und die fortgeschrittene Nutzung zu lernen!

Schreibe einen Kommentar

Deine E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind mit * markiert