Letztes Jahr hab ich einen // TODO: fix later Kommentar in eine Codebase geschrieben. Booking-Service, Retry-Logik. Schneller Hack, Freitagnachmittag, Sprint-Ende. “Mach ich Montag.”
Montag kam. Ich hab’s nicht gemacht.
Drei Monate später: git log --all --oneline | grep "TODO" | wc -l ergab 47. Siebenundvierzig TODOs. Nicht alle von mir. Aber der erste war von mir. Und als ich den Code vom Kollegen gesehen hab, der seine Retry-Logik genau so hacky geschrieben hat wie ich, direkt neben meinem Hack — da wusste ich: das war nicht sein Fehler. Das war mein Signal.
The Pragmatic Programmer beschreibt genau diesen Moment. Und obwohl das Buch von 1999 ist, trifft es Dinge die ich 25 Jahre später noch falsch mache.
Die Sache mit den kaputten Fenstern
Es gibt diese Studie aus den 80ern. Gebäude mit einem einzigen kaputten Fenster verfallen schneller als identische Gebäude ohne. Nicht weil das kaputte Fenster strukturellen Schaden anrichtet. Sondern weil es ein Signal sendet: hier kümmert sich niemand.
Software hat dieselbe Dynamik. Aber sie ist subtiler, weil du den Verfall nicht siehst. Du riechst ihn nicht. Du merkst ihn erst wenn ein neuer Entwickler im Team anfängt und nach zwei Wochen fragt: “Warum ist das alles so… so?”
Mein Booking-Service-Hack war ein kaputtes Fenster. Was danach passierte, Schritt für Schritt:
- Woche 1: Mein
// TODO: fix laterin der Retry-Logik - Woche 3: Kollege schreibt Error-Handling im selben Service, ähnlich hacky. Sein PR-Kommentar: “Analog zur bestehenden Retry-Logik”
- Woche 6: Neuer Microservice braucht ähnliche Logik. Copy-Paste aus dem Booking-Service. Inkl. Hack.
- Woche 11: Jemand schlägt vor, die Retry-Logik in eine Shared Library zu extrahieren. Den Hack. Als Library.
Vom TODO zum institutionalisierten Workaround in elf Wochen.
“Don’t leave ‘broken windows’ unrepaired. Fix each one as soon as it is discovered.”
Das Buch hat recht. Aber es unterschlägt etwas: manchmal kannst du das Fenster nicht reparieren. Nicht am Freitag um 17 Uhr mit einem Deployment-Freeze vor dir. Und hier wird der Rat ein bisschen naiv. In der Realität hast du Deadlines, Stakeholder die auf Features warten, und eine Retry-Logik die funktioniert, nur halt hässlich. Was dann?
Was bei mir funktioniert hat: wenn ich den Hack nicht sofort fixen kann, schreib ich nicht // TODO. Ich schreib ein Ticket. Mit Akzeptanzkriterien. Und ich setz es in den nächsten Sprint. Nicht weil ich besonders diszipliniert bin, sondern weil TODOs im Code unsichtbar werden. Tickets in Jira sind unangenehm sichtbar. Und unangenehm sichtbar ist genau was du willst.
Der umgekehrte Effekt ist real. Ich hab in einem Projekt gearbeitet, das obsessiv sauber war: 100% Lint-Compliance, kein einziger TODO im Code. Ich hab mich geschämt, dort unsauberen Code zu committen. Qualität erzeugt sozialen Druck. In beide Richtungen.
Aber hier ist die unbequeme Wahrheit: du machst das gerade. Irgendwo in deiner Codebase gibt es einen Hack den du vor Wochen geschrieben hast. Du weißt welchen. Und du weißt, dass inzwischen jemand anders daneben was Ähnliches gebaut hat.
Die perfekte API die niemand brauchte
Zweite Geschichte, anderes Team.
Payment-API. Vier Entwickler, drei Monate. Jeder Edge Case abgedeckt: Partial Refunds mit Währungskonvertierung, idempotente Retry-Logik mit Idempotency Keys, Rate Limiting pro Merchant mit konfigurierbaren Tiers, Error Responses nach RFC 7807. 94% Test Coverage. Wunderschön.
Tag 1 in Production: 11 Requests. Elf. Davon 8 vom internen Healthcheck.
Die drei echten Requests haben alle denselben Endpoint benutzt: POST /payments. Keiner hat Partial Refunds gebraucht. Keiner hat die Währungskonvertierung benutzt. Keiner hat die konfigurierbaren Rate-Limiting-Tiers angefasst.
Drei Monate Arbeit. Drei Requests.
Das Buch sagt dazu:
“Great software today is often preferable to the fantasy of perfect software tomorrow.”
Und:
“Know when to stop.”
Das ist der Satz, der mir nicht mehr aus dem Kopf geht. Nicht “schreib schlechten Code.” Sondern: hör auf wenn es gut genug ist. Die Frage ist immer: gut genug für wen?
Ein internes Admin-Tool das drei Leute benutzen? Da reicht ein Handler, ein HTML-Template, und go run main.go. Ein Payment-System das echtes Geld bewegt? Da brauchst du Idempotency, Audit Logs, und Monitoring. Aber du brauchst das alles erst wenn du Nutzer hast die es brauchen.
Die vier Entwickler hätten in zwei Wochen eine API shippen können, die POST /payments und GET /payments/:id macht. Zwei Endpoints. Dann warten was die Merchants wirklich brauchen. Stattdessen haben sie drei Monate lang ihre eigenen Annahmen implementiert.
Perfektionismus in Software ist meistens keine hohen Standards. Es ist Angst. Angst, dass jemand einen Edge Case findet den du nicht abgedeckt hast. Angst vor einem Sentry-Alert. Angst vor dem Code Review. Und du baust diese Angst in drei Monate Arbeit ein, die niemand benutzt.
Harte Frage: welches Feature baust du gerade, von dem du schon weißt dass es wahrscheinlich niemand braucht?
Wo das Buch nervt
Ich hab The Pragmatic Programmer letztes Jahr nochmal gelesen und vieles trifft. Aber ein Kapitel geht mir auf die Nerven: das Knowledge Portfolio.
Die Idee: behandle dein Wissen wie ein Finanzportfolio. Diversifiziere. Investiere regelmäßig. Lern jedes Jahr eine neue Sprache. Lies Bücher außerhalb deiner Bubble.
Klingt gut. Stimmt auch grundsätzlich. Aber der Rat ignoriert eine Realität: die meisten von uns arbeiten 40+ Stunden, haben neben dem Job noch ein Leben, und die Idee “lern jedes Jahr eine neue Sprache” ist für jemanden mit zwei Kindern und einem Projekt in Crunch-Phase ungefähr so hilfreich wie “schlaf einfach mehr.”
Was tatsächlich funktioniert: tiefe Expertise in dem was du täglich machst, kombiniert mit gelegentlichen Ausflügen in angrenzende Gebiete. Nicht Rust lernen weil es auf Hacker News trendet. Sondern die Postgres-Docs lesen, weil du jeden Tag Queries schreibst und nicht weißt was ein Bitmap Heap Scan ist.
Das Buch kommt aus einer Zeit, in der ein Senior-Entwickler vielleicht C, Perl und ein bisschen SQL konnte. Heute ist der Stack so breit, dass “diversifizieren” oft bedeutet: noch eine Sache halbwegs können statt eine Sache wirklich verstehen.
Zwei Dinge aus dem Buch, die du diese Woche machen kannst:
-
grep -r "TODO\|FIXME\|HACK" src/ | wc -l— führ das in deiner Codebase aus. Wenn die Zahl dreistellig ist, such dir die drei ältesten raus und mach Tickets draus. Nicht fixen. Tickets. Sichtbar machen. -
Schau dir das Feature an, an dem du gerade arbeitest. Frag dich: wenn ich das in der Hälfte der Zeit shippe, mit der Hälfte der Edge Cases, würde es trotzdem Wert liefern? Wenn ja, ship die Hälfte.