Debugging, Monitoring und Code-Qualität: Tools in der Web-Entwicklung

"Ich roll' dann mal aus" Hilko Holweg  –  11 Kommentare

Auch in der Web-Entwicklung von heise online geht nicht immer alles auf Anhieb glatt. Mit den Jahren haben sich diverse Tools zum Debugging, Monitoring und zum Steigern der Code-Qualität etabliert.

Was wäre das für eine schöne Welt, in der man Code schreibt, dazu ein paar Tests, alle möglichen Sicherheitsprobleme bedacht hat, Usability-, Accessibility- und Performance-Aspekte bereits mitgedacht hat und noch dazu alles im einheitlichen Stil wie der Rest der Abteilung verfasst hat? So ganz ohne Unterstützung klappt das meist jedoch nicht.

Zum einen schaffen es immer wieder Bugs in den produktiven Code, denen wir dann auf die Schliche kommen müssen. Zum anderen versuchen wir natürlich auch bereits in der Entwicklung dafür zu sorgen, dass sich die Qualität unseres Codes verbessert und wir Bugs und andere Probleme möglichst vermeiden, statt sie später fixen zu müssen.

Bei der Entstehung

Bereits im Editor prüfen Lint-Plug-ins den Code gegen unsere Lint-Regeln, für JavaScript ist unsere Konfiguration auch im öffentlichen Repository verfügbar. Die gemeinsamen Lint-Regeln helfen vor allem gegen unterschiedliche Stile in einer Code-Basis, aber auch um Flüchtigkeitsfehler zu vermeiden. Gehört die öffnende geschweifte Klammer nun noch in die Zeile des if oder eher in eine eigene Zeile darunter? Klare Lint-Regeln beugen diesen Diskussionen vor – das gilt auch für die alte Frage "Tabs oder Spaces?".

Darüber hinaus gibt es diverse Unit- und Integrationstests – je nach Sinnhaftigkeit. In einigen Projekten haben wir Pre-Commit- und Pre-Push-Hooks, die noch einmal prüfen, ob es keine Lint-Probleme oder Fehler im Test gibt. Bei Projekten, in denen wir Release Automation nutzen, helfen solche Pre-Commit-Hooks, auch Commit-Messages zu vermeiden, die nicht konform mit der Release Automation sind.

Speziell für unser Frontend-Framework akwa haben wir noch das Tool akwaDebug, was in der Entwicklung und im Live-System eingeschaltet werden kann und dann detailliertere Auskunft über seine Abläufe gibt, was gerade bei kniffligen Problemen schon mal sehr hilfreich sein kann.

Wo wir Critical-CSS im Einsatz haben, prüft schon beim Entwickeln ein Eintrag im performance-Abschnitt der Webpack-Config während des Build-Prozesses, dass unsere gesteckten Dateigrößengrenzen nicht überschritten werden. Für AMP-Projekte ist das sogar ein Muss, da nur 75 KByte CSS erlaubt sind.

Eine GitLab-CI Pipeline mit mehreren Stages und einem erfolgreichen "lint"-Task.

CI Stages

Hat der Code seinen Weg in die gemeinsame Versionsverwaltung gefunden, laufen die Tests (noch mal) durch. Bei einem Merge Request prüft nach einem Commit eine SonarQube-Instanz, ob durch den Merge sich die Code-Basis verschlechtern würde. SonarQube schaut einerseits auf Code-Qualität (Code-Smells, Accessibility-Probleme, Code-Duplikationen etc.), aber auch auf Sicherheitsrisiken.

Bei unserer Einführung von SonarQube wurden wir erst mal überhäuft von Fehlern und Warnungen. Aber davon sollte man sich nicht einschüchtern lassen. Zum einen mussten wir zu Beginn die Konfiguration an unsere Bedürfnisse anpassen. Zum anderen waren viele Probleme eher kleinerer Natur. So machten sich einige bei uns einen Sport daraus immer mal wieder zwischendurch einen ganzen Batzen von Warnungen und Fehlern zu beseitigen und damit Bereiche auf 0 zu bringen. Prinzipiell lässt sich SonarQube aber so einstellen, dass es den aktuellen Code-Zustand zum Zeitpunkt der Einführung als Basis betrachtet und einen Merge Request durchwinkt, wenn dieser nicht mehr Fehler oder Warnungen erzeugt.

Eine SonarQube-Analyse, wie man sie gerne liest: alles bestanden! Nach jedem Push ins GitLab prüft SonarQube und kommentiert mit einem Analyse-Bericht.

Bugs nach Release? Nein! Doch! Oh!

Nach dem Release hofft nun jede Entwicklerin und jeder Entwickler, dass es keine (weiteren) Bugs gibt, doch trotz Sorgfalt zeigt die Erfahrung, dass dem nicht immer so ist. Um Problemen im Cluster auf den Grund zu gehen, hilft uns das Tool Sentry, welches Code-Monitoring im Live-Betrieb ermöglicht, inklusive Stack-Traces und Kontext-Informationen. So kann man beispielsweise auch sehen, ob bei einem Fehler ein einzelner Task sehr lange gedauert hat, und es ermöglicht einem, direkt an dieser Stelle anzusetzen, um dem Ursprung des Fehlers nachzugehen. Auf dieselbe Art lassen sich auch Performance-Flaschenhälse aufspüren, bevor sie zum ausgewachsenen Problem werden.

Infrastruktur

Irgendwo muss der Code ja auch laufen, und das sind in der Regel letztlich Server. Doch auch da kann es mal knirschen. Für ein generelles Monitoring der Systeme haben wir Icinga2 laufen, was beim Überschreiten von Grenzwerten auch gleich Alarm schlägt. Für sinnvolle Visualisierungen von Time-Series-Data nutzen wir Grafana-Dashboards. Gerade wenn Fehlerursachen noch gesucht werden müssen, ist es gut, schnell auf einen Blick sehen zu können, wann sich der Zustand des Systems, beispielsweise die Serverlast, merklich verändert hat. Zur allgemeinen Logdaten-Suche und -Recherche greifen wir auf Kibana zurück. Unser Kubernetes-Cluster haben wir mit einem eigenen Monitoring ausgestattet und vertrauen hier derzeit auf Prometheus.

In Summe sind das ganz schön viele Tools, doch haben sie alle ihre Daseinsberechtigung, da jedes bei unterschiedlichen Aufgaben hilft. Auch muss sich nicht jede Person mit jedem dieser Tools im Detail auskennen, manche Tools sind für bestimmte Gruppen unserer Abteilung relevanter als andere.

Zum Schluss würde uns auch interessieren, womit unsere Leserinnen und Leser ihre Erfahrungen gemacht haben: Welche Tools setzt ihr ein? Auf welches Tool möchtet ihr in der Entwicklung für Debugging, Monitoring und Qualitätssicherung nicht mehr verzichten? Schreibt es gerne in die Kommentare.