Aktualisierung eines Kanboard-Pods

Dies ist der letzte Artikel in meiner kleinen Reihe, über meinen Ausflug ins Container-Land, zur Bereitstellung der Anwendung Kanboard.

Wie meine Reise ins Container-Land begonnen hat, kann in „Kanboard im Container…“ nachgelesen werden. Wie man einen Reverse-Proxy vor einem Pod betreibt sowie mit dem Thema Backup und Restore habe ich mich inzwischen ebenso beschäftigt. Letzteres habe ich zum Glück implementiert und getestet, bevor ich mit der Dokumentation Datenverlust erlitten habe. Damit die Anwendung nach einem Neustart automatisch startet und für ein bisschen Komfort, habe ich Systemd-Service-Units generiert. In diesem Teil geht es nun um die Aktualisierung dieser Umgebung.

Umgebung

Aktuell läuft Kanboard 1.2.18 auf einer RHEL 8 VM. Zur Ausführung sind folgende Werkzeuge und Container-Images beteiligt.

$ podman --version
podman version 2.2.1
$ podman images
REPOSITORY                              TAG      IMAGE ID      CREATED        SIZE
registry.redhat.io/rhel8/postgresql-96  latest   4ce7daa6dc1d  7 weeks ago    451 MB
docker.io/kanboard/kanboard             v1.2.18  e7ee6403944b  3 months ago   58.6 MB
k8s.gcr.io/pause                        3.2      80d28bedfe5d  14 months ago  688 kB

Um mir die Erstellung eines Pods und das Einhängen von Podman-Volumes zu erleichtern, nutze ich folgendes kleines Skript:

#!/bin/bash
podman run -d --pod new:kanboardpod --name kanboard --privileged -p 127.0.0.1:8080:80 -v kanboard_datadir:/var/www/app/data:Z -v kanboard_pluginsdir:/var/www/app/plugins:Z kanboard/kanboard:v1.2.18

podman run -d --pod kanboardpod --name pgsql_db -e POSTGRESQL_USER=<USERNAME> -e POSTGRESQL_PASSWORD=<Verrate ich nicht> -e POSTGRESQL_DATABASE=kanboard -v pgsql_dbdir:/var/lib/pgsql/data:Z rhel8/postgresql-96:1-107

Mein Pod und die drei dazugehörigen Container werden während der folgenden Schritte noch normal ausgeführt.

Die Container selbst sind dabei zustandslos. Die persistent zu speichernden Daten werden in Podman-Volumes im lokalen Dateisystem der VM abgelegt.

Vorgehensweise

Ich verzichte in diesem Fall bewusst auf podman-auto-update(1), da ich mir erstmal einen Überblick verschaffen möchte, was denn generell zu tun ist und wie die einzelnen Schritte aussehen können. Die grundsätzliche Reihenfolge für ein Update sieht dabei wie folgt aus:

  1. Aktuelle Container-Images aus einer Registry holen (podman-pull(1))
  2. Laufende Pod-Instanz stoppen und entfernen (podman-pod(1))
  3. Neue Pod-Instanz mit angepasstem Wrapper-Skript erstellen
  4. Systemd-Service-Units erneut generieren (podman-generate-systemd(1))
  5. Pod-Instanz stoppen
  6. Generierte Systemd-Service-Unit starten

An dieser Stelle möchte ich vorweg nehmen, dass es genau so einfach war, wie es sich anhört. Die neuen Container-Images habe ich mit folgenden Kommandos heruntergeladen.

$ podman pull docker.io/kanboard/kanboard:v1.2.19
Trying to pull docker.io/kanboard/kanboard:v1.2.19...
Getting image source signatures
Copying blob 0c2b98bb5f7e done
Copying blob ca3cd42a7c95 done
Copying blob e994ab432c32 done
Copying blob 7b30337f40d2 done
Copying blob f58d66ecc40b done
Copying config 2cb48121b7 done
Writing manifest to image destination
Storing signatures
2cb48121b7437ba15cd984472754b300395026c3e09e7c659b4f9b62e5b5b4dd

$ podman pull registry.redhat.io/rhel8/postgresql-96:1-127
Trying to pull registry.redhat.io/rhel8/postgresql-96:1-127...
Getting image source signatures
Copying blob 64607cc74f9c done
Copying blob 320ae7fa06a7 done
Copying blob 13897c84ca57 done
Copying blob b3b2bbe848df done
Copying config 9c6ab01c14 done
Writing manifest to image destination
Storing signatures
9c6ab01c14748f7ff79483759122cb28e0f2c8b0310e5c8d9b5af8383e91f163

$ podman images
REPOSITORY                              TAG      IMAGE ID      CREATED        SIZE
docker.io/kanboard/kanboard             v1.2.19  2cb48121b743  4 days ago     61.3 MB
registry.redhat.io/rhel8/postgresql-96  1-127    9c6ab01c1474  2 weeks ago    449 MB
registry.redhat.io/rhel8/postgresql-96  latest   4ce7daa6dc1d  7 weeks ago    451 MB
docker.io/kanboard/kanboard             v1.2.18  e7ee6403944b  3 months ago   58.6 MB
k8s.gcr.io/pause                        3.2      80d28bedfe5d  14 months ago  688 kB

Mit den folgenden Befehlen werden Informationen zum laufenden Pod angezeigt, der Service wird gestoppt und der Pod inkl. seiner Container entfernt.

$ podman pod ls
POD ID        NAME         STATUS   CREATED      INFRA ID      # OF CONTAINERS
2f3aa7d07e6e  kanboardpod  Running  4 weeks ago  34e8479a2847  3

$ systemctl --user stop pod-kanboardpod.service

$ podman pod ls
POD ID        NAME         STATUS  CREATED      INFRA ID      # OF CONTAINERS
2f3aa7d07e6e  kanboardpod  Exited  4 weeks ago  34e8479a2847  3

$ podman pod rm kanboardpod
2f3aa7d07e6eb7d4c3a0c9927dac222be52b8992f95929c12af8ce4afafd4eb1

In mein Wrapper-Skript (siehe Abschnitt Umgebung) trage ich die neuen Versionsnummern bei den entsprechenden Aufrufen ein:

#!/bin/bash
podman run -d --pod new:kanboardpod --name kanboard --privileged -p 127.0.0.1:8080:80 -v kanboard_datadir:/var/www/app/data:Z -v kanboard_pluginsdir:/var/www/app/plugins:Z kanboard/kanboard:v1.2.19

podman run -d --pod kanboardpod --name pgsql_db -e POSTGRESQL_USER=<USERNAME> -e POSTGRESQL_PASSWORD=<Verrate ich nicht> -e POSTGRESQL_DATABASE=kanboard -v pgsql_dbdir:/var/lib/pgsql/data:Z rhel8/postgresql-96:1-127

Nachdem das obige Wrapper-Skript ausgeführt wurde, prüfe ich, ob die neue Pod-Instanz läuft, erstelle die Service-Units und aktiviere diese:

$ podman pod ls
POD ID        NAME         STATUS   CREATED             INFRA ID      # OF CONTAINERS
85273ee9bb82  kanboardpod  Running  About a minute ago  82f45a722dff  3

$ podman container ls
CONTAINER ID  IMAGE                                         COMMAND         CREATED             STATUS                 PORTS                   NAMES
6becc68a9c20  registry.redhat.io/rhel8/postgresql-96:1-127  run-postgresql  About a minute ago  Up About a minute ago  127.0.0.1:8080->80/tcp  pgsql_db
82f45a722dff  k8s.gcr.io/pause:3.2                                          About a minute ago  Up About a minute ago  127.0.0.1:8080->80/tcp  85273ee9bb82-infra
e72ca46110be  docker.io/kanboard/kanboard:v1.2.19                           About a minute ago  Up About a minute ago  127.0.0.1:8080->80/tcp  kanboard

$ podman generate systemd --files --name kanboardpod
/home/bob/pod-kanboardpod.service
/home/bob/container-kanboard.service
/home/bob/container-pgsql_db.service

$ mv *.service .config/systemd/user/

$ podman pod stop kanboardpod
85273ee9bb82e49e236ae37d9320fd95af1eb186d7d965d72b9e2a270ca5cedf

$ systemctl --user daemon-reload
$ systemctl --user start pod-kanboardpod.service

Fazit

Das war einfacher als gedacht. Oder anders formuliert, es hat tatsächlich so funktioniert, wie ich es erwartet habe.

Mein kleines Wochenend-Projekt skaliert sicher nicht gut und ist als Beispiel für Produktionsumgebungen vermutlich weniger geeignet. Doch um Software als rootless-Container auszuführen und in kleinem Umfang zu testen, scheint dieser Weg durchaus geeignet zu sein.

Vielleicht schiebe ich in Zukunft noch einen Artikel unter Verwendung von podman-auto-update(1) nach.

Schreibe einen Kommentar

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