Breaking Changes: Warum sich jedes Update riskant anfühlt – und wie man daraus Routine macht

#Breaking Changes Software-Update

Gründer & Lead Developer

Experte für Softwareentwicklung und Legacy-Code-Optimierung

LinkedIn

Das Risiko von Breaking Changes bei Software-Updates ist der Grund, warum so viele Teams irgendwann leise aufhören, Dinge zu aktualisieren. Ein Dependency-Bump, der auf dem Papier routinemäßig aussah, legt den Checkout an einem Freitagnachmittag drei Stunden lahm. Ein Minor-Versionssprung in einem Framework verändert, wie Datumsangaben geparst werden, und niemand merkt es, bis ein Kunde darauf hinweist, dass eine Rechnung das falsche Fälligkeitsdatum zeigt. Nach zwei oder drei solchen Vorfällen wird "Updates lassen wir erstmal" zur Standardantwort – und sie bleibt deutlich länger bestehen, als irgendjemand ursprünglich vorhatte.

Dabei geht es nicht wirklich um schlechte Entwickler. Es geht um Systeme, die nie darauf ausgelegt wurden, Updates sicher zu machen, und darum, keine Möglichkeit zu haben, herauszufinden, ob eine Änderung etwas kaputtgemacht hat, bevor ein Kunde es tut.

Das Risiko von Breaking Changes, auf das niemand plant

Die meisten Updates scheitern nicht am Update selbst. Eine gepatchte Bibliothek, ein neues Framework-Release, ein geänderter Konfigurations-Default – das wird meist schon von den jeweiligen Maintainern getestet, bevor es ausgeliefert wird. Was Breaking Changes in der eigenen Anwendung sichtbar macht, ist fast immer etwas, das niemand im eigenen Team eingeplant hat. Ein Randfall, von dem der eigene Code abhängt und von dem die Maintainer der Bibliothek nie wussten. Ein Konfigurations-Default, der sich still zwischen Versionen geändert hat. Oder einfach Monate kleiner Änderungen, die sich angesammelt haben, seit zuletzt jemand die Dependency-Liste angefasst hat.

Das Muster, das am häufigsten zu beobachten ist: Ein Team pinnt Versionen, um Update-Probleme zu vermeiden – das funktioniert eine Weile, bis ein Sicherheitspatch das Update trotzdem erzwingt. Nur sind es jetzt ein Dutzend Versionssprünge statt einem, und alle kleinen Kompatibilitätsprobleme, die sich sonst nach und nach gezeigt hätten, tauchen auf einmal auf – in Produktion, während eines Release-Fensters, das niemand bewusst gewählt hat.

Ungetestete Systeme machen aus jedem Update eine Vermutung

Gibt es keinen automatisierten Weg zu prüfen, ob ein Update das Verhalten verändert hat, bleibt als einziger Test die Produktion. Das ist kein Plan. Das ist eine Wette, und die Quoten werden schlechter, je länger Updates aufgeschoben werden, weil sich mehr Änderungen zwischen der eingesetzten Version und der Zielversion ansammeln.

Teams in dieser Lage entwickeln oft eine Art Vorsicht, die wie Disziplin aussieht, aber keine ist. Jemand erinnert sich, dass ein Update einmal den Zahlungsprozess kaputtgemacht hat, also wird jedes Update jetzt für einen Samstagmorgen angesetzt, mit jemandem in Bereitschaft, nur für den Fall. Das ist kein Sicherheitsnetz. Das ist die Bereitschaft, nach einem Ausfall aufzuräumen, statt ihn vorher abzufangen. Die tatsächliche Lösung ist günstiger und deutlich weniger dramatisch: einen Weg bauen, um zu wissen, ob ein Update etwas kaputtgemacht hat, bevor es irgendjemanden außerhalb des Teams erreicht.

Smoke-Tests fangen die relevanten Ausfälle in Minuten statt in Tagen ab

Ein Smoke-Test ist keine vollständige Testsuite und muss es auch nicht sein. Es ist ein kurzer, schneller Check, der bestätigt, dass die zentralen Abläufe nach einer Änderung noch funktionieren: Ein Nutzer kann sich einloggen, ein Kauf geht durch, das Hauptdashboard lädt mit echten Daten statt einer Fehlerseite. Diesen Check ein bis zwei Minuten nach jedem Update laufen zu lassen, liefert die Antwort lange bevor ein Kunde sie liefert.

Die meisten Systeme, die wir nach einem fehlgeschlagenen Update untersuchen sollten, hatten überhaupt keine automatisierten Tests, geschweige denn einen Smoke-Test – die ehrliche Antwort auf "hat das Update etwas kaputtgemacht" war also "wir wissen es erst, wenn uns jemand Bescheid sagt". Ein Smoke-Test dreht das um. Er fängt nicht alles ab; das tut kein schneller Check. Aber er fängt genau die Ausfälle ab, die sonst ein zentrales Feature vor zahlenden Kunden lahmlegen würden – und er fängt sie ab, bevor das Update überhaupt in Produktion ankommt.

Eine Staging-Umgebung hilft nur, wenn sie die Wahrheit sagt

Viele Teams haben bereits eine Staging-Umgebung und werden trotzdem in Produktion überrascht, weil Staging der Produktion nicht nahe genug ähnelt, um aussagekräftig zu sein. Eine kleinere Datenbank, Drittanbieter-Integrationen, die auf Sandbox-Konten zeigen, andere Traffic-Muster, manchmal sogar eine andere Version der Laufzeitumgebung selbst. Ein Update kann Staging sauber durchlaufen und trotzdem in Produktion scheitern – aus Gründen, die nichts mit dem Update zu tun haben und alles damit, dass die beiden Umgebungen von vornherein nicht vergleichbar sind.

Das zu beheben erfordert kein perfektes Abbild der Produktion. Es erfordert, dass Staging eine realistische Datenmenge vorhält, mit denselben Kategorien externer Dienste spricht, von denen das Live-System abhängt, und auf denselben Versionen von allem darunter läuft wie die Anwendung selbst. Sobald das stimmt, bedeutet ein sauberer Durchlauf in Staging tatsächlich etwas – und genau das macht aus einem Update einen Sprung ins Ungewisse einen Schritt, den man bereits einmal erfolgreich beobachtet hat.

Kleine Batches machen aus einem großen Risiko mehrere kleine

Das Update, das auf dramatische, schwer zu diagnostizierende Weise etwas kaputtmacht, ist fast nie eine einzelne, kleine, isolierte Änderung. Es ist ein Batch: ein Dutzend Dependency-Bumps, die nach Monaten des Aufschiebens gemeinsam aufgelaufen sind, ein großer Framework-Versionssprung statt der drei kleineren davor, eine Datenbankmigration, die mit einem nicht verwandten Feature-Release gebündelt wurde. Geht etwas in diesem Batch kaputt, bedeutet die Ursachensuche, sich rückwärts durch alles zu arbeiten, was gleichzeitig ausgeliefert wurde.

Updates in kleinen Batches durchzuführen, eine Abhängigkeit oder einen Versionsschritt nach dem anderen, mit einem Smoke-Test nach jedem Schritt, bedeutet, dass ein Ausfall direkt auf seine Ursache zeigt. Jedes einzelne Update trägt außerdem weniger Risiko, weil sich weniger verändert hat seit dem letzten bekannten guten Zustand. Teams, die diese Gewohnheit annehmen, aktualisieren tendenziell häufiger statt seltener, weil jedes Update aufhört, ein Ereignis zu sein, und zur Routine-Wartung wird – was es die ganze Zeit hätte sein sollen.

Wie eine funktionierende Routine aussieht

Setzt man diese Gewohnheiten zusammen, ist die Form einer funktionierenden Update-Routine klar: Abhängigkeiten werden in kleinen, regelmäßigen Batches aktualisiert statt in großen periodischen Schüben, eine produktionsnahe Staging-Umgebung führt nach jedem Batch einen Smoke-Test aus, und nichts erreicht die Produktion, bevor dieser Smoke-Test sauber durchläuft. Nichts davon entfernt das Risiko vollständig. Software verändert sich, und gelegentlich rutscht trotzdem etwas durch einen soliden Prozess. Was sich ändert, ist, dass die Entdeckung eines Ausfalls von einem Support-Ticket eines Kunden zu einem Fünf-Minuten-Check wird, den das eigene Team durchführt, bevor irgendjemand außerhalb der Firma etwas davon mitbekommt.

Wenn ein Team Updates vermeidet, weil die letzten paar schlecht gelaufen sind, liegt das Problem wahrscheinlich nicht am Update-Prozess selbst. Es liegt daran, dass kein Sicherheitsnetz darunter liegt. Warum niemand eure Abhängigkeiten aktualisiert behandelt die organisatorische Seite, wie sich diese Vermeidung überhaupt erst aufbaut, und ein Code-Qualitäts-Audit ist ein sinnvoller nächster Schritt, wenn eine externe Einschätzung gewünscht ist, wie nah das eigene Staging- und Test-Setup daran ist, den nächsten Ausfall abzufangen, bevor er ausgeliefert wird. Für Teams, deren Update-Probleme eher am Alter der Codebasis liegen als am Prozess drumherum, adressiert Legacy-Code-Optimierung die strukturelle Seite desselben Problems.

Wer Hilfe dabei möchte, einen Smoke-Test und eine echte Update-Routine einzurichten, bevor der nächste Sicherheitspatch die Frage erzwingt, meldet sich unter hello@wolf-tech.io oder schaut vorbei auf wolf-tech.io.