Suche
Über den bewussten Umgang mit technischer Qualität

Codequalität: "Funktioniert" ist nicht genug

Nils Wloka

Budgetzwänge, fachliche wie technische Komplexität und volatile Anforderungen gehören zum Projektalltag der IT-Branche. Gleichzeitig predigen moderne Vorgehensmodelle Geschäftswert und Anwenderfokus. In dieser Gemengelage vergessen wir allzu leicht die Hauptzutat erfolgreicher Projekte: Programmcode. Über den bewussten Umgang mit dieser Zutat jenseits des Entwicklerteams möchte ich hier sprechen.

Wenn Sie die aktuellen IT-Trends verfolgen, hören und lesen Sie viel über Architekturen, Methoden und Techniken: Cloud Computing, Scrum und Kanban, dieses Framework und jene Programmiersprache. Das sind alles wichtige und faszinierende Themen, aber je mehr Teams und Projekte ich in meiner Rolle als Coach begleite, desto stärker empfinde ich das Bedürfnis, für eine bewusstere und breitere Auseinandersetzung mit der ebenso selbstverständlichen wie, in der allgemeinen Wahrnehmung, zunehmend als „gelöst“ und „unspektakulär“ betrachteten Tätigkeit des Programmierens zu werben. Im Folgenden möchte ich daher eine Brücke zu den Ideen modernen Programmierhandwerks insbesondere für diejenigen unter den Lesern schlagen, die aufgrund ihrer Rolle sonst wenig Einblick in die „Implementierungsdetails“ ihrer Projekte haben.

Was geht mich das an?

Meiner Erfahrung nach finden die handwerklichen Aspekte der Softwareentwicklung unter Nichtprogrammierern aus zwei Gründen häufig keine Betrachtung: Zum einen lässt sich argumentieren, dass hochqualifizierte Entwickler und Softwarearchitekten durchaus ohne äußeres Zutun in der Lage sind, angemessene technische Qualität sicherzustellen. Und tatsächlich gibt es Initiativen, die sich ausgiebig mit der Weiterentwicklung und Verfeinerung von Programmierpraktiken auseinandersetzen. In der Realität jedoch arbeiten Entwicklungsteams nicht im kontextfreien Raum, und während des gesamten Projektlebenszyklus werden von allen Beteiligten immer wieder weitreichende Entscheidungen gefällt. Viele der Tätigkeiten, die sich unter Programmierern als richtig und notwendig durchgesetzt haben, sind aber nur schwer durchzusetzen, wenn aus politischen und organisatorischen Gründen inkompatible Rahmenbedingungen etabliert wurden. Zum anderen gibt es schlichtweg häufig keine Lobby für technische Qualität. Wörter, wie „Over-Engineering“, „goldene Wasserhähne“ und „Technikverliebtheit“ machen die Runde. Was zählt, sind sichtbare Ergebnisse. Wir zitieren den Benutzer, der mit Konzepten wie sauberem Programmcode wenig anzufangen weiß und führen Herstellungskosten und Budgetzwänge als Argument an. Interessanterweise sind diese Ansichten für sich genommen auf den ersten Blick stichhaltig und im Sinne der häufig anzutreffenden Rollenverteilung in Softwareprojekten auch richtig. Trotzdem wird in der Praxis aus mit besten Vorsätzen und großem Enthusiasmus begonnenen Projekten viel zu häufig eine Wartungshölle, an der sich alle Beteiligten aufreiben.

Hauptsache, es funktioniert!

Wieso gehen Softwareprojekte aber immer wieder in diese Falle? Software hat eine perfide Eigenschaft: Nichtentwickler können von „außen“ praktisch nicht erkennen, in welchem Zustand sie sich befindet. Software rostet und klappert nicht, wenn die Verarbeitung schlecht ist. Weder fängt sie an zu stinken, wenn ihr Haltbarkeitsdatum abgelaufen ist, noch funktioniert sie zwangsläufig schlechter, solange auf Funktionalität fokussierte Qualitätssicherung betrieben wurde. Verwundert es da, wenn sich die Frage aufdrängt, ob diese, scheinbar nur für einen kleinen Kreis sichtbare, technische Qualität überhaupt eine Rolle spielen sollte? Hauptsache, es funktioniert! Gleichzeitig fällt es leichter, die diffusen, durch sinkende Entwicklerproduktivität und mangelnder Softwarewartbarkeit verursachten Kosten zu akzeptieren, als den abgrenzbaren Aufwand, den qualitätssichernde und -steigernde Maßnahmen verursachen. Dadurch wird fast zwangsläufig jede Aktivität im Umfeld dieser ominösen internen Qualität zu einem Einsparungspotenzial. Auf der anderen Seite scheinen Projekte früher oder später zwangsläufig in eine Situation zu geraten, in der jedes Einsparungspotenzial realisiert werden muss: „Sportliche“ Aufwandsschätzungen haben einen unerfüllbaren Erwartungsdruck aufgebaut, „Scope Creep“ frisst Budgetreserven auf, übereifrige, agile Missionare predigen Hyperproduktivität. Und tatsächlich ist im Fall der Softwareentwicklung schneller ja auch immer besser.

Technische Schulden

Leider gibt es ein Problem, dass sich wohl am besten mit der von Ward Cunningham geprägten Metapher der „technischen Schulden“ („technical debt“ [1]) beschreiben lässt: Wenn wir anfangen, mehr Produktivität auszugeben, als uns aufgrund unserer Fähigkeiten und der Komplexität des zu lösenden Problems zur Verfügung steht, häufen wir technische Schulden an. Technische Schulden haben viele Gesichter: Fehlendes Softwaredesign, unzureichende Test- oder Projektautomatisierung, unsauberer Code oder unbeabsichtigte Komplexität sind häufig anzutreffende Facetten. Gemein ist allen Formen technischer Schulden, dass sie zu einem Verschleiß der Software führen. Dieser Verschleiß wiederum erschwert die Weiterentwicklung und erhöht das Risiko von Regressionsfehlern. Dadurch werden Zinsen fällig (Kasten: „Zinsen auf technische Schulden“), die Nettoproduktivität sinkt. Tilgen wir nicht durch geeignete Maßnahmen, kommt es im schlimmsten Fall zur Überschuldung. Erweiterungen an der Software werden unbezahlbar, Projekte müssen abgebrochen, bestehende Softwaresysteme ohne funktionalen Mehrwert abgelöst werden. Hier schließt sich der Kreis: Der auf den ersten Blick rationale Versuch, durch unbedingte Beschleunigung schneller ans Ziel zu kommen, führt auf der kurvigen Strecke eines Softwareentwicklungsprojekts bisweilen in den Straßengraben.

[ header = Seite 2: Zinsen auf technische Schulden ]

Zinsen auf technische Schulden

Exemplarisch möchte ich einige häufig anzutreffende „Zinsarten“ und die ihnen zugrundeliegenden Formen technischer Schulden erwähnen:

  • Regressionsfehler, die erst außerhalb der Entwicklung festgestellt werden, deuten auf mangelnde Automatisierung funktionaler Tests hin.
  • Stark überschrittene Aufwandsschätzungen insbesondere bei weniger komplexen Arbeitspaketen deuten auf unsauberen oder schlecht faktorierten Code oder unklares Design hin.
  • Lange Debugging-Sessions in Kombination mit schwer lokalisier- und nachstellbaren Fehlerfällen sind ein Zeichen für geringe Unit-Test-Abdeckung.

Das Ziel

Im Umkehrschluss kann aber ein bewusster Umgang mit technischer Qualität erhebliche Vorteile bieten. Für den Projektverantwortlichen bedeutet nachhaltig entwickelte Software:

  • Aufwandsschätzungen werden präziser, wenn keine versteckten Risiken in der Software selbst liegen.
  • Die Produktivität bleibt über alle Phasen des Projekts konstant, wenn Entwickler nicht von Altlasten ausgebremst werden.
  • Das Softwaresystem wird gegenüber Änderungen flexibel, wenn das Design sorgfältig durchdacht und kontinuierlich gepflegt wird.
  • Neue Projektmitarbeiter können einfacher eingearbeitet werden, wenn der Code sauber und lesbar ist.
  • Nachbesserungen und Regressionsfehler sowie die damit verbundenen Planungsunsicherheiten können vermieden werden, wenn Abnahmekriterien konsequent automatisiert getestet werden.
  • Technische Schulden und die damit kurzfristig realisierbaren Produktivitätsschübe werden zu einem gezielt taktisch einsetzbaren Instrument, wenn die „Qualitätsbilanz“ des Projekts für alle sichtbar ist.

Ähnlich Vorteile ergeben sich für Kunden oder Produktverantwortliche:

  • Die bessere Wartbarkeit sauber hergestellter Software wirkt sich positiv auf Gesamtkosten und Lebensdauer aus.
  • Wenn Änderungen sich mit besser vorhersehbarem und geringerem Aufwand realisieren lassen, können Geschäftschancen besser genutzt werden.

Hinzu kommt der menschliche Aspekt. Beobachtet man Teams, die über lange Zeit an Software mit schlechter interner Qualität arbeiten, stellt man fast immer entweder einen hohen Stresspegel oder sehr geringe Motivation fest. So genannter „Legacy Code“, also Software, in der hohe technische Schulden angesammelt sind oder die sich bereits im Zustand der Überschuldung befindet, stellt eine erhebliche Belastung für die Entwickler dar: Nachbesserungen, Debugging und gefühlt mangelhafte Produktivität sind an der Tagesordnung. Gleichzeitig lässt ein Softwaresystem ab einem bestimmten Verfallsgrad auf den ersten Blick kaum noch kosteneffiziente Verbesserungen zu. Für den Entwickler entsteht ein Teufelskreis, in dem er durch schlechte interne Qualität gezwungen ist, mehr technische Schulden anzuhäufen, um überhaupt noch produktiv zu sein. Wenn dieser Teufelskreis unterbrochen wird, kann man praktisch immer einen deutlichen Anstieg der Mitarbeitermotivation mit allen damit verbundenen Vorteilen beobachten.

Was können wir tun?

Wie aber kann man zu etwas beitragen, das man direkt weder wahrnehmen noch steuern kann? Meiner Meinung nach ist die entscheidende Frage, was ich in einer leitenden oder organisierenden Funktion tun kann, um den bewussten Umgang mit Qualität zu begünstigen. Betrachte ich die Projekte und Teams, mit denen ich in der Vergangenheit gearbeitet habe, sind letztlich immer wieder die gleichen Muster zu beobachten:

  • Es mangelt an Erfahrung mit qualitätssteigernden und -bewahrenden Entwicklungspraktiken.
  • Es existiert kein einheitliches Qualitätsverständnis.
  • Aus gefühltem Zeitdruck werden als sinnvoll wahrgenommene Praktiken nicht angewandt.
  • Das Projekt befindet sich im Zustand der oben erwähnten Überschuldung.

Den letztgenannten, in der Praxis leider häufig anzutreffenden, Aspekt möchte ich zugunsten einer ausführlicheren Betrachtung der übrigen Punkte an dieser Stelle bewusst aussparen. Mit dem Problem des, liebevoll „historisch gewachsen“ genannten, Softwaresystems setzt sich in großer Tiefe das von Michael Feathers verfasste Buch „Working Effectively with Legacy Code“ auseinander [2]. Ideen für den Umgang mit den verbleibenden Herausforderungen möchte ich in den folgenden Abschnitten vermitteln.

Software Craftsmanship

Erfreulicherweise hat sich um das Thema nachhaltiger Softwareentwicklung in den letzten Jahren eine rege Szene entwickelt. Die Software-Craftsmanship-Bewegung beschäftigt sich mit dem Programmieren als ein erlernbares Handwerk. Ihre Thesen sind an das agile Manifest [3] angelehnt und erweitern dieses (Kasten: „Modernes Programmierhandwerk“).

[ header = Seite 3: Modernes Programmierhandwerk ]

Modernes Programmierhandwerk

Unter der Überschrift „Die Latte höher legen“ hat die Software-Craftsmanship-Bewegung [4] sich das Praktizieren und Weitergeben professioneller Softwareentwicklung auf die Fahne geschrieben und hebt dabei vier Aspekte hervor:

  • Gute handwerkliche Arbeit
  • Stetige Produktion von Geschäftswert
  • Eine Gemeinschaft von Fachleuten
  • Produktive Partnerschaften mit dem Kunden

Vorreiter dieser Bewegung sind Meinungsführer, wie Robert C. Martin (unter anderem Autor von „Clean Code“ [5]) und Corey Haines (Organisator des Global Day of Coderetreat 2011 [6]). Der von der Bewegung betriebenen Auseinandersetzung mit modernem Programmierhandwerk entspringen neben Handlungsprinzipien und -praktiken auch neue Lern- und Lehransätze.

Ermangelt es den Mitarbeitern an dem, für einen konstruktiven Umgang mit interner Qualität notwendigen, Handwerkszeug, so kann man hier auf einen großen Fundus von Literatur, Schulungen und Maßnahmen zurückgreifen. Exemplarisch seien Aktivitäten erwähnt, mit denen ich in den vergangenen Jahren gute Erfahrungen gemacht habe: In Leserunden, in denen ein Buch gemeinsam in Abschnitten gelesen und diskutiert wird, lässt sich neben theoretischen Grundlagen auch ein gemeinsames Verständnis von Softwarequalität schaffen. Durch variable Dauer und Frequenz der Veranstaltungen eignet sich diese Lernmethode besonders gut für Mitarbeiter, die stark durch Projekte ausgelastet sind. Eine ausgezeichnete Zusammenstellung geeigneter Bücher kann man auf Stack Overflow finden [7]. Diese zwei Titel empfehle ich gerne:

  • „Clean Code: A Handbook of Agile Software Craftsmanship“ von Robert C. Martin
  • „Refactoring: Improving the Design of Existing Code“ von Martin Fowler

Eine auf den ersten Blick ungewöhnliche Lernmethode ist das Lehren. Wer schon einmal eine Schulung vorbereitet oder einen Fachartikel geschrieben hat, weiß jedoch, wie viel man dabei selbst dann noch über ein Thema lernen kann, wenn man sich bereits für einen Experten hält. Lehren kann in den unterschiedlichsten Formen stattfinden. Sehr gut funktionieren beispielsweise „Tech Talks“ (Frontalvorträge zu einem speziellen Thema, etwa im Rahmen oder angrenzend an ein Abteilungstreffen), Vorbereitung oder Aktualisierung internen Schulungsmaterials und Mentorentätigkeiten (Betreuung neuer Mitarbeiter, Studenten oder Auszubildender).

Ein in der Software-Craftsmanship-Szene immer wieder betonter Aspekt ist das bewusste Üben der Programmiertätigkeit. Ein professioneller Pianist spielt schließlich nicht nur auf der Konzertbühne Klavier, sondern verwendet einen (in diesem Fall vermutlich sehr großen) Teil seiner Zeit auf das Üben seines Handwerks. Speziell für die Tätigkeit des Programmierens hat sich das Format des Coding Dojos [8] durchgesetzt. In diesen Treffen werden gemeinsam spezielle, Code Kata [9] genannte, Programmierübungen durchgeführt. Wie auch die Leserunden sind Coding Dojos ein flexibles und abwechslungsreiches Format, das im Rahmen so genannter Code Retreats und auf Konferenzen mittlerweile auch öffentlich und zum Teil kostenfrei angeboten wird.

Bewusster arbeiten

Falls entsprechende Erfahrung bereits vorhanden ist oder Grundlagen beispielsweise durch die oben genannten Maßnahmen geschaffen wurden, gilt es, ein einheitliches Qualitätsverständnis zu schaffen. Im Sinne der von W. Edwards Deming vertretenen Thesen ist es notwendig, eine Kultur zu etablieren, in der Qualität „eingebaut“ wird, statt mangelnde Qualität durch Kontrollen auszusieben [10]. Da wir in der Softwareentwicklung nicht von klassischen Produktionsprozessen ausgehen können, müssen wir Systeme schaffen, in denen ein geeignetes Qualitätsniveau zum Selbstverständnis werden kann. Letztlich geht es darum, das Erlernte in den Arbeitsalltag zu integrieren. Mit den folgenden Aktivitäten habe ich in der Vergangenheit gute Erfahrungen gemacht:

Ein in der IT-Branche zunehmend beliebtes Verfahren sind so genannte Retrospektiven [11]. Durch einen Moderator (in diesem Kontext häufig „Facilitator“ genannt) wird ein geschützter und formalisierter Rahmen für Rückblick, Analyse und Veränderung geschaffen. Ergebnisse der Retrospektive fließen in den nächsten Arbeitsabschnitt ein und werden hinsichtlich ihrer Wirksamkeit überprüft. Bezogen auf den hier beschriebenen Veränderungsprozess können sie Raum bieten, um sich offen und intensiv mit der eigenen Arbeitsweise und dem eigenen Qualitätsverständnis auseinanderzusetzen.

Eine weniger ritualisierte Form der Reflexion bieten so genannte Brown-Bag-Seminare oder Lunch-and-Learn-Treffen. Hier werden im Rahmen einer gemeinsamen Mahlzeit vorher festgelegte oder spontan ausgewählte Themen diskutiert. Hier eignet sich besonders die von Michael D. Hill als „Lottery Learning“ [12] beschriebene Variante, in der ein zufällig ausgelostes Teammitglied ein Stück Quellcode auswählt, über das in lockerer Form diskutiert wird.

Ebenfalls einfach umzusetzen und wenig zeitaufwändig sind regelmäßige Termine, zu denen das Team für einen festgelegten Zeitraum (beispielsweise eine Stunde) ausschließlich an einem bestimmten Qualitätsaspekt, beispielsweise der Behebung bestimmter Designmängel oder der Erhöhung der Testabdeckung, arbeitet. So lässt sich der natürlichen Erosion des Programmcodes entgegenwirken, während gleichzeitig erlernte Fähigkeiten in der Praxis vertieft und zur Gewohnheit werden.

Begleitend zu allen genannten Maßnahmen hat sich der Einsatz eines Coachs als ausgesprochen hilfreich erwiesen. Jenseits der Methoden klassischer Beratung kann er nicht nur Teams helfen die selbstgesteckten Ziele zu erreichen, sondern auch zwischen Rollen vermitteln. Grundsätzlich sind zwei Arten des Coachings denkbar: Als Personalverantwortlicher kann ich Mitarbeitern den Freiraum lassen, sich in die Rolle des internen Coachs hineinzuentwickeln. Die nötigen Fähigkeiten kann man sich, eine gewisse Kommunikationsfertigkeit vorausgesetzt, beispielsweise auf Coach Camps [13] aneignen. Als Qualifikation ist entsprechend weniger eine vollständige Durchdringung des Themas aus fachlicher Sicht notwendig, als vielmehr die Akzeptanz innerhalb der Mannschaft. Alternativ gibt es heute eine wachsende Zahl externer Coachs, die sich auf das Thema Programmierhandwerk spezialisiert haben.

[ header = Seite 4: Wir haben doch keine Zeit ]

Wir haben doch keine Zeit

Zuletzt möchte ich ein interessantes, nicht selten in den von der Auseinandersetzung mit technischer Qualität ausgelösten Transformationsprozessen zu beobachtendes, Phänomen ansprechen: Das empfundene Spannungsgefüge zwischen Qualität und Wirtschaftlichkeit. Hier spielen meiner Meinung nach mehrere Aspekte zusammen:

Häufig werden die Kosten der Veränderung selbst (beschrieben im Satir-Veränderungsmodell [14] und in der IT-Branche als „Improvement Ravine“ [15] bekannt) mit den Kosten für qualitätsschaffende Maßnahmen vermengt, anstatt unter dem Gesichtspunkt der Weiterbildung und Personalentwicklung betrachtet zu werden. Auch kann in der Regel zusätzlicher Aufwand (beispielsweise durch qualitätsschaffende Maßnahmen und Sanierung) einfacher beziffert werden, als zusätzlicher Nutzen (beispielsweise durch höhere Wartbarkeit der Software sowie Motivation und Produktivität der Entwickler). Werden gleichzeitig die durch Qualitätsmängel entstehenden Probleme (etwa Nachbesserungen und Produktivitätsverluste) nicht gegengerechnet, entsteht schnell ein verzerrtes Bild.

In Diskussionen, die ich mit Projekt- und Budgetverantwortlichen führe, stelle ich häufig fest, dass dadurch Qualität primär von der Kostenseite betrachtet wird. Sicher gibt es so etwas wie „zu viel“ Qualität. In der Realität bleibt leider zu beobachten, dass ein Qualitätsniveau, das diese Sorge rechtfertigen würde, in den meisten Fällen nicht vorliegt. Vielfach führt dann die schwer fassbare und zum Teil kontraintuitive Natur technischer Qualität zu einer gefährlichen Situation: So wie ein Flugzeug, dass an Höhe verliert, weil es zu langsam fliegt, durch das Zurückziehen des Steuerhorns nicht steigt, sondern im Gegenteil weiter an Geschwindigkeit verliert, wird ein Projekt, das durch Qualitätsprobleme ins Trudeln geraten ist, nicht durch Einsparungen an qualitätssichernden Maßnahmen aufgefangen.

Um festzustellen, in welchem Zustand sich ein Projekt befindet, empfehle ich eine systematische Betrachtung der durch Qualitätsmängel entstehenden Kosten sowie ein Explizit-Machen technischer Schulden. Qualitätsbedingte Kosten können in Form von Aufwand für „zinsbedingte“ Tätigkeiten (Kasten: „Zinsen auf technische Schulden“) gesondert erfasst werden. Die Höhe der angesammelten technischen Schulden lässt sich einfach und effektiv sichtbar machen, indem jeder Verzicht auf notwendige qualitätssichernde Maßnahmen als Arbeitspaket mit einer Aufwandsschätzung für die Tilgung gleichberechtigt verwaltet wird. Konsequent auf die Metapher der technischen Schulden übertragen, ergibt sich eine Aufstellung von Zinsen und Restschuld, die mir eine objektive Betrachtung, und damit auch eine belastbare Entscheidung für mehr oder weniger Qualität, ermöglicht.

Viel von dem Zeitdruck, der mit dem wichtigen Ziel der Wirtschaftlichkeit unnötig und wegen fehlender Datengrundlage aufgebaut wird, lässt sich so vermeiden. Um es mit Robert C. Martin zu sagen: „I will go fast by going well“ [16].

Ist dieses Selbstverständnis hergestellt, kann ich als Projektleiter die künstliche und schädliche Trennung von qualitätswirksamen und funktionsschaffenden Maßnahmen fallen lassen. Genauso wenig, wie ich im Restaurant Tellerwäsche und Küchenhygiene als optionale Extras mit Aufpreis angeboten bekomme, kann ich als Verantwortlicher für ein Softwareprojekt Design, Refaktorierung und Testautomatisierung zur Disposition stellen, indem ich sie als von der „eigentlichen“ Softwareentwicklung getrennte Tätigkeiten betrachte und behandele. Von einer Diskussion über das Für und Wider von Qualität bewege ich mich hin zu einer konstruktiven Diskussion über das richtige Maß.

Schlusswort

Ich hoffe, ich konnte Ihnen mit diesem Artikel näher bringen, warum eine bewusste Auseinandersetzung mit dem Programmierhandwerk auch und gerade dann Sinn ergibt, wenn Sie IT-Projekte hauptsächlich in einer leitenden oder organisierenden Rolle begleiten. Wenn Sie sich über diesen Überblick hinaus mit dem Thema beschäftigen wollen, bieten die im Text referenzierten Quellen viele interessante Informationen und Denkanstöße.

Geschrieben von
Nils Wloka
Kommentare

Schreibe einen Kommentar

Deine E-Mail-Adresse wird nicht veröffentlicht.