Ich beobachte ja immer mit einer Mischung aus Entsetzen und Faszination, wie Firmen sich in irgendwelche Komplexitätsmonster hineinsteigern. Häufig aus einem völlig absurden Wunsch heraus, "mehr wie Google" oder "mehr wie Netflix" zu sein.

Da hat jemand gelesen, wie geil Google angeblich skaliert, und was für einen tollen Zoo aus Microservices Netflix hat. Das brauchen wir hier auch!

Erst glaubten alle, sie bräuchten unbedingt Virtualisierung. Damit sie Server umziehen können. Hat jemals jemand von denen eine VM umgezogen? Eher selten bis gar nicht.

Dann glaubten alle, sie brauchen Kubernetes. Für ihre Flotte von Microservices. Wofür braucht ihr denn so viele Microservices? Isoliert und sandboxt ihr da Operationen voneinander? Nein. Soll das die Cores besser ausnutzen? Warum denn, wieviele User habt ihr denn pro Sekunde? Oh. Zehn? Hrmjanunäh.

Zumindest letzteres kann man über Reddit nicht sagen. Die haben genug Benutzer, um sich über Skalierbarkeit ernsthaft Gedanken machen zu müssen. Und im Allgemeinen flutscht deren Site ja auch, fühlt sich nicht träge an. Aber neulich war die mal für ein paar Stunden weg. Umso erfreulicher, dass es am Ende ein Post-Mortem gab.

Das Ergebnis ist: Sie haben einen Kubernetes-Cluster updaten wollen, und das Update flog ihnen um die Ohren. Naja, äh, kein Ding, denkt ihr euch jetzt vielleicht. Sowas macht man ja immer rollbackbar. Dafür hat man ja Microservices. Damit die einzelnen Einheiten eine möglichst kleine Granularität haben und man da einzeln Herumupdaten kann. Überhaupt sollte Kubernetes ja noch am problemärmsten hoch- und runter-schiebbar sein, denn da liegen ja alle gefährdeten Daten in Pods. Wir reden hier vom Kubernetes selbst, das sie geupdated haben. Würde man denken. Tatsächlich ist es aber so:

But, dear Redditor… Kubernetes has no supported downgrade procedure. Because a number of schema and data migrations are performed automatically by Kubernetes during an upgrade, there’s no reverse path defined.

I-de-ale Voraussetzungen für ein Stück kritische Infrastruktur! Diese Enterprise-Fuzzys labern immer rum von wegen Verfügbarkeit und Metriken und setzen dann … sowas ein?!?

Tsja. Nächstes Problem: Alle Metriken waren ausgefallen. Heutige Installationen sind so krass ultrakomplex, dass man da ohne Metriken nicht mehr so richtig diagnostizieren kann. Gut, wenn die Metriken ganz weg sind, dann klingt das nach einem Netzwerkproblem. War es dann auch.

At some point, we noticed that our container network interface, Calico, wasn’t working properly.

Wieso haben sie das nicht sofort gemerkt, fragt ihr? Tsja. Da fehlte die institutionelle Erfahrung. Die hatten lauter Leute, die wussten, wie sie in ihrem Admin-Interface Dinge klickt. Aber was man tut, wenn das Admin-Interface nicht geht, weil das Netz dazwischen braun ist, das wusste keiner mehr, und inzwischen war die Komplexität so krass gewachsen, dass das wahrscheinlich generell niemand mehr von Hand gucken konnte. Sie haben da tolle selbstreparierende Prozesse gehabt, aber das lief halt wie bei Asimov. Wenn du selbstwartende Dinge baust, geht das Wissen verloren, wie man sie baut und wartet, weil das ja nicht mehr gebraucht wird, und wenn die dann irgendwann doch kaputt gehen, hast du dann halt komplett verloren. So war das auch hier. Sie haben den Pod mit dem Netzwerkmanagement-Kram gekillt und gelöscht und der versuchte sich dann neu zu installieren, aber die Installation hatte halt dasselbe Problem wie die davor.

Also haben sie ein Backup einzuspielen versucht. Aber wie bei Asimov:

Once that was finished, we took on the restore procedure, which nobody involved had ever performed before, let alone on our favorite single point of failure.

Das ist generell nicht gut. Ein Backup ist erst dann ein Backup, wenn man es erfolgreich wieder einspielen konnte. Wenn man das nie probiert hat, dann ist das auch kein Backup sondern bloß ein Datenhaufen.

This procedure had been written against a now end-of-life Kubernetes version, and it pre-dated our switch to CRI-O, which means all of the instructions were written with Docker in mind.

Wie das halt ist, wenn man essentielle Dinge hinten runterfallen lässt, weil das ja alles selbstheilend ist und wir daher nicht so gut vorbereitet sein müssen.

Was ich persönlich ja besonders unterhaltsam finde, ist dass sie dann über TLS-Zertifikate stolperten, weil sie ein Backup für Kiste A auf Kiste B eingespielt haben, und dann hatte der ein Zertifikat für die falsche Maschine und Clients wollten nicht mehr connecten.

Aber der eigentliche Kracher an dieser ganzen Story ist, was am Ende der Root Cause war. Achtung, stabil hinsetzen:

The nodeSelector and peerSelector for the route reflectors target the label `node-role.kubernetes.io/master`. In the 1.20 series, Kubernetes changed its terminology from “master” to “control-plane.” And in 1.24, they removed references to “master,” even from running clusters. This is the cause of our outage. Kubernetes node labels.

Das ganze Kartenhaus ist eingestürzt, weil Kubernetes aus Wokenessgründen fand, dass da nicht mehr master stehen darf. Kubernetes, muss man an der Stelle wissen, hat ja historisch enorm viel mit Sklaverei zu tun hat. Und wenn man böse Worte nicht mehr verwendet, macht man damit böse Taten in der Vergangenheit rückgängig. Oder so.

Deshalb war Reddit kaputt.

Update: Oh und erwähnte ich, dass sie beim Ausführen der veralteten Dokumentation, wie man Backups einspielt, merkten, dass eines der Kommandozeilentools seit dem die Argumente umbenannt hatte? Was zur Hölle ist denn das für eine unprofessionelle Kackscheiße schon wieder! Was denken sich denn bitte solche Leute?! Unseren Scheiß wird schon keiner einsetzen?

24.03.2023