Im Artikel Der Rewrite-Reflex haben wir uns gefragt, warum Entwickler beim Anblick einer gewachsenen Codebasis sofort neu schreiben wollen – und warum das meistens ein Fehler ist. Die Alternative lautet: verstehen statt ersetzen. Schrittweise Entflechtung. Abhängigkeiten sichtbar machen. Vorhandenes Wissen bewahren.
Das ist der Weg. Aber wohin führt er?
Wann ist man fertig? Wann hört Legacy auf, Legacy zu sein?
Ich habe lange gebraucht um zu merken, dass ich diese Frage nie wirklich gestellt hatte. Und als ich sie stellte, merkte ich: die meisten können sie nicht beantworten.
Die bekannteste Definition – und ihre Grenzen
Die Standardantwort kommt von Michael Feathers, aus seinem Buch Working Effectively with Legacy Code (2004):
"Legacy code is code without tests."
Die Definition ist eingängig. Sie macht das Problem messbar. Und sie hat der Branche geholfen – weil sie Tests als Werkzeug der Modernisierung in den Mittelpunkt gerückt hat.
Aber sie hat einen blinden Fleck.
Betrachten wir Yii 3, das am 31. Dezember 2025 veröffentlicht wurde. Es hat:
- ~100% PHPUnit-Coverage über alle Packages
- Psalm auf höchstem Level – jede Zeile statisch analysiert
- Infection Mutation Testing – Tests die nicht nur Coverage messen, sondern beweisen dass sie Fehler finden würden
Per Feathers' Definition ist Yii 3 das Gegenteil von Legacy. Es ist vielleicht das am besten getestete PHP-Framework überhaupt.
Und trotzdem: würdest du heute ein neues Großprojekt auf Yii 3 aufbauen?
Die Frage zögert. Und das Zögern ist die Antwort.
Was Feathers nicht gemessen hat
Yii 3 ist technisch makellos. Aber:
- Die Community ist klein
- Laravel und Symfony haben den Markt der aktiv wachsenden Frameworks unter sich aufgeteilt
- Entwickler mit Yii-3-Erfahrung sind schwer zu finden
- Für neue Projekte ist es selten die erste Wahl
Das ist eine Dimension von Legacy die 2004 noch nicht existierte – oder zumindest nicht sichtbar war: Ökosystem-Legacy.
Code der perfekt geschrieben ist, vollständig getestet, architektonisch vorbildlich – aber am Rand des Ökosystems. Niemand schreibt darüber. Niemand sucht Entwickler dafür. Die Kurve zeigt nicht nach oben.
Feathers hat Code gemessen. Was er nicht gemessen hat: die Beziehung zwischen Code und der Welt um ihn herum.
Die vollständigere Frage
Legacy ist kein binärer Zustand. Es ist ein Verhältnis – zwischen Code, Team, Ökosystem und Zeit.
Dasselbe Stück Code kann gleichzeitig sein:
- Technisch solid – gut strukturiert, lesbar, getestet
- Ökosystem-Legacy – das Framework darunter hat keine wachsende Community mehr
- Wissens-Legacy – die Entwickler die es geschrieben haben, sind längst weg
- Kontext-Legacy – die Anforderungen von damals existieren so nicht mehr
LimeSurvey auf Yii 1.1 ist ein gutes Beispiel für alle vier Dimensionen gleichzeitig. Der Code funktioniert. Er ist im Einsatz. Er hat eine aktive Community. Und er trägt das Gewicht von Entscheidungen, die 2012 richtig waren.
Ist das Legacy? Ja – in manchen Dimensionen. Nein – in anderen.
Die Frage "Wann hört Legacy auf, Legacy zu sein?" setzt voraus, dass es einen klaren Endpunkt gibt. Einen Moment wo man sagen kann: jetzt ist es fertig. Jetzt ist es modern.
Diesen Moment gibt es nicht.
Der Code von heute ist das Legacy von morgen
Das ist keine pessimistische Aussage. Es ist eine ehrliche.
Software existiert nicht in einem Vakuum. Sie existiert in einer Umgebung die sich verändert – PHP-Versionen, Framework-Generationen, Team-Zusammensetzungen, Anforderungen, Community-Trends. Was heute modern ist, ist in fünf Jahren der Code den jemand anders anfassen muss und denkt: hier muss man irgendwann mal was machen.
Das haben wir im Yii-Artikel gesehen: Yii 1.1 war 2010 revolutionär. Yii 2 war 2014 der Stand der Kunst. Yii 3 ist 2025 architektonisch vorbildlich – und trotzdem am Rand.
Jede Generation war zu ihrer Zeit richtig. Und jede Generation wurde irgendwann zu dem, was die nächste Generation überwinden wollte.
Was dann das Ziel ist
Wenn Legacy kein Zustand ist der endet, sondern ein Verhältnis das sich verändert – was ist dann das Ziel der Modernisierung?
Ich glaube es sind drei Dinge, die zusammenkommen müssen:
1. Der Code soll die Arbeit nicht behindern. Das Stichwort ist Cognitive Load – die kognitive Last die ein Entwickler trägt, bevor er überhaupt anfangen kann zu arbeiten. Nicht null Bugs, nicht perfekte Architektur. Sondern: wer eine neue Anforderung umsetzt, soll nicht erst stundenlang rekonstruieren müssen wie der Code zusammenhängt. Jede globale Funktion ohne klaren Kontext, jede Abhängigkeit die nirgends explizit ist, jede Klasse die zu viel weiß – das ist kognitive Last. Sie summiert sich. Und irgendwann übersteigt sie die Kapazität des Teams.
2. Das Wissen soll im Code stecken – nicht in den Köpfen.
Robert C. Martin nennt es Screaming Architecture: eine Codebasis soll schreien was sie tut. Wer application/helpers/common_helper.php öffnet, hört kein Schreien. Er hört ein leises Murmeln von 130 Funktionen die irgendwie zusammengehören – aber niemand sagt warum, für wen, und in welchem Kontext. Modernisierung bedeutet: Wissen externalisieren. In Typen, in Struktur, in Tests, in Namen die etwas bedeuten. Jede Funktion die nur noch eine Person versteht, ist ein Risiko. Jede Abhängigkeit die im Kopf statt im Code lebt, ist eine versteckte Schuld.
3. Der nächste Schritt soll immer möglich sein. Software die nicht im Fluss ist, stirbt. Kein großer Schnitt, kein Rewrite – aber auch kein Stillstand. Die Codebasis soll in einem Zustand sein der Veränderung erlaubt, ohne dass jede Änderung ein Zittern auslöst. Das ist keine Frage der Perfektion. Es ist eine Frage der Richtung: morgen ein kleines Stück besser als heute. Übermorgen wieder. Das ist kein Endpunkt – es ist ein Aggregatzustand.
Zurück zu LimeSurvey
Nach sechs Artikeln über LimeSurvey – über common_helper.php, über PHPStan-Analysen, über 11.339 Aufrufe veralteter Funktionen, über Yii 1.1 und seine Geschichte – was ist der Befund?
LimeSurvey ist Legacy in dem Sinne, dass viele Entscheidungen von gestern den Code von heute prägen. Die common_helper.php ist das sichtbarste Beispiel. Yii::app() als Gottobjekt ist ein weiteres. Globale Funktionen statt Service-Klassen. Prozeduraler Code neben MVC.
Aber LimeSurvey ist auch ein Beweis dafür, dass Software überlebt – durch wechselnde Teams, PHP-Versionen, Framework-Generationen, Anforderungen. Das ist nicht trotz des Codes. Das ist auch wegen ihm. Wegen den Entwicklern die ihn geschrieben haben, mit dem Wissen das sie hatten, unter dem Druck der herrschte.
Legacy-Code ist kein Versagen. Er ist der Beweis, dass Software überlebt hat.
Das habe ich im Rewrite-Reflex-Artikel geschrieben. Ich stehe dazu.
Aber Überleben ist kein Ziel. Es ist eine Voraussetzung.
Das Ziel ist: der Code soll morgen besser sein als heute. Nicht perfekt. Nicht modern im Sinne des aktuellen Zeitgeists. Sondern ein kleines Stück klarer, ein kleines Stück verständlicher, ein kleines Stück weniger hinderlich.
Jeden Tag. Ohne Endpunkt. Ohne den Moment wo man sagt: jetzt ist es fertig.
Denn den gibt es nicht.
Die eigentliche Antwort
Wann hört Legacy auf, Legacy zu sein?
Wenn man aufhört, es als Problem zu sehen – und anfängt, es als Ausgangspunkt zu verstehen.
Nicht als Zustand der überwunden werden muss. Sondern als der Ort, von dem aus die nächste Verbesserung beginnt.
Das ist unbefriedigend für jeden der eine klare Checkliste erwartet. Aber es ist ehrlich. Und in der Softwareentwicklung ist Ehrlichkeit über den eigenen Code meistens wertvoller als die Illusion eines Endpunkts.