Java Magazin   11.2014 - Logging

Erhältlich ab:  Oktober 2014

Autoren / Autorinnen: 
Tobias Flohre ,  
Arno Haase ,  
Volker Gruhn ,  
Stefan TilkovTill Schulte-Coerne ,  
,  
Heinz KabutzSven Ruppert ,  
Diana Kupfer ,  
Mark StrubergGerhard Petracek ,  
Christian Grobmeier ,  
Lars RöwekampArne Limburg ,  
Christian Grobmeier ,  
Sascha Möllering ,  
Michael Müller ,  
Lars RöwekampArne Limburg ,  
Dominik Obermaier ,  
Eva Fulierova ,  
Dominik Schadow ,  
Johannes Dienst ,  
Jonathan BuchJoachim Arrasz ,  
Tammo van Lessen ,  
Kai Tödter ,  
Peter Friese

Vom Open-Source-Modell sind sie schon lange überzeugt. Doch erst kürzlich legten sie ein gemeinsames Bekenntnis zu offenen Technologien ab, dessen Symbolkraft kaum zu übertreffen ist: Zehn große Tech-Firmen aus dem Silicon Valley schmiedeten Mitte September die neue Allianz „TODO“, die sich der Entwicklung und Pflege von Open-Source-Technologien widmen möchte. Auf der Entwicklerkonferenz @Scale präsentierte Jay Parikh, Global Head of Engineering bei Facebook, der Öffentlichkeit die gemeinsame Vision. Das auf der Website veröffentlichte Selbstverständnis der Kooperation beginnt wie folgt: „Open source is part of the fabric of each of our companies. Between us, our open source programs enable us to use, contribute to, and maintain, thousands of projects – both large and small.“

Talk openly, develop openly

TODO ist ein Akronym für „Talk openly, develop openly.“ So lautet die zentrale Forderung der zehn Gründungsmitglieder des Bündnisses: Box, Dropbox, Facebook, GitHub, Google, Khan Academy, Stripe Square, Twitter und Walmart Labs.

Die Liste an Open-Source-Technologien aus dem Hause Facebook wird immer länger: HHVM, Hack, Presto oder Cassandra sind einige Beispiele. Auch die quelloffenen Technologien von Google – von A wie Android bis Z wie ZXing – sind bekannt und bewährt. In puncto Android musste sich der Suchmaschinenriese allerdings schon mehrmals den Vorwurf gefallen lassen, sein mobiles Betriebssystem sei zu strengen Auflagen unterworfen und daher nicht wirklich Open Source.

Mehr als eine Taskforce

In Reaktion auf die kritische OpenSSL-Schwachstelle „Heartbleed“, die im Frühjahr publik wurde, gründeteten Google und Facebook sowie weitere Unternehmen die Core Infrastructure Initiative, die sich um die Finanzierung wichtiger Open-Source-Projekte kümmert. Auch die Gründung von TODO dürfte viele Kratzer im Image des Open-Source-Modells, die Fälle wie Heartbleed hinterlassen haben, ausmerzen. Im Selbstverständnis ist von „Herausforderungen“ die Rede, die man gemeinsam bewältigen wolle: „These [open source] programs face many challenges, including ensuring high-quality and frequent releases, engaging with developer communities, and using and contributing back to other projects effectively. The members of this group are committed to working together in order to overcome these challenges.“

TODO ist jedoch mehr als eine Taskforce für Open-Source-Problemfälle. Das oben zitierte Statement „Open source is part of the fabric of each of our companies“ zeigt: Offene Technologien sind zu einer unverzichtbaren Geschäftsgrundlage für die erfolgreichsten IT-Unternehmen der Erde avanciert – und haben einen Ritterschlag wie diesen verdient. Man könnte auch sagen: Das goldene Open-Source-Zeitalter ist angebrochen.

Java Logging und Lava Jogging

Eine neue Ära könnte auch die im Juli erschienene zweite Major-Version des Java-Logging-Frameworks ­Apache Log4j einläuten, die Teil des Heftschwerpunkts der vorliegenden Ausgabe ist. Noch vor zwei Jahren scherzte Viktor Klang, Chief Architect bei Typesafe: „Java Logging and Lava Jogging – both are things to avoid.“ Auf Twitter kam dieser bissige Schüttelreim gut an. Zur selben Zeit war Log4j-Bashing noch gang und gäbe. Schließlich kam die zweite Hauptversion gefühlte zehn Jahre zu spät. Schon vor fast zwei Jahren prophezeite unser Autor Christian Grobmeier optimistisch, Version 2.0 werde Log4j das „Comeback des Jahres“ bescheren. „Welchen Jahres?“ wäre rückblickend eine durchaus berechtigte Frage gewesen. Nun aber ist ­Log4j 2.0 nach vier Jahren harter Entwicklungsarbeit da – und „bietet (...) alles, was man heutzutage zum Loggen braucht“, wie Grobmeier in seinem Artikel ab S. 45 berichtet. Mit seiner Audit-Fähigkeit, Java-5-Concurrency-Features, einer schöneren Konfiguration, einem modernen API und dem neuen asynchronen Logger auf Basis der LMAX-Disruptor-Technologie hat der Java-Logging-Veteran tatsächlich einige Trümpfe im Ärmel.

Zunächst aber beantworten Joachim Arrasz und Jonathan Buch in ihrem Leitartikel ab S. 32 viel grundsätzlichere Fragen zum Thema Logging – etwa die, warum klassisches Logging eigentlich so schwer ist und den Betrieb oftmals mehr behindert als unterstützt. Auch werfen wir u. a. einen Blick auf Logging in verteilten Umgebungen: Das Projekt Apache Flume macht’s möglich (S. 40). Wie auch immer Sie es mit Java Logging halten: Möge der Heftschwerpunkt dazu beitragen, alte Vorurteile abzubauen und neue Wege zu entdecken. Keep loggin’!

kupfer_diana_sw.tif_fmt1.jpgDiana Kupfer, Redakteurin

Website Twitter Google Xing

Reactive Programming, Microservices, Message-oriented Middle­ware und andere moderne Architekturansätze fordern von Entwicklern heutzutage bei der Auswahl ihrer Tools mehr Weitblick, mehr (Ein-)Blick in die Produktion und deren Anforderungen, als noch vor einigen Jahren. Alle diese Ansätze bringen üblicherweise die Möglichkeit einer besseren Verteilung der gesamten Anwendung mit sich. Dies hat aber beträchtliche Auswirkungen auf den Betrieb von Anwendungen dieser Art.

Innerhalb dieser Miniserie wollen wir die hierdurch entstehenden Anforderungen an Entwickler, als auch an die eingesetzten Tools selbst genauer unter die Lupe nehmen. Zum Ende eines jeden Artikels versuchen wir uns an einer möglichst objektiven Bewertung der Werkzeuge im jeweiligen Einsatzszenario.

Da aber viele miteinander interagierende Tools vorgestellt werden, müssen wir uns auf eine Beschreibung und eine Bewertung beschränken und wollen mit den Artikeln das Zusammenspiel und die Funktionsweise beschreiben (Abb. 1). Für konkretere Einblicke in die Tools wollen wir gern auf speziellere Artikel verweisen, vielleicht können wir ja die Neugier wecken. Einige Leser werden nun denken „Warte, dafür haben wir doch DevOps, was interessiert mich das“, aber warten wir den Verlauf der Serie ab. Und wer hier den nächsten Vergleich schwergewichtiger Application Server und deren Leistungsvermögen erwartet, den müssen wir leider enttäuschen und auf ältere Artikel verweisen.

arrasz_abb1.eps_fmt1.jpgAbb. 1: Reise durch die Entstehung (das Development), über die Stabilisierungsphase der Preproduktion, bis hin zur Produktion

Weiterhin wollen wir unsere Leser noch darauf aufmerksam machen, dass wir die komplette Serie auf www.JAXenter.de begleiten werden und auch für Diskussionen rund um das Thema zur Verfügung stehen.

Beginnen wir nun im ersten Teil mit den Werkzeugen zum Logging aus Anwendungen, der Konfiguration von Logging sowie der Kumulierung von Logs über verschiedene Dienste, (Micro-)Services oder auch Server hinweg. Warum beginnen wir ausgerechnet mit Logging?

Logging ist wohl derjenige Teil der Implementierung, bei dem am offensichtlichsten eine Verbindung zwischen Entwicklern und Betreibern besteht. Üblicherweise versuchen Teamplaner dies heute mit dem Buzzword „DevOps“ zu erschlagen. DevOps in Cross-functional Teams sollen die Verbindung zwischen Entwicklung und Betrieb stabilisieren. Sie sollen den Gedanken des Betriebs und der betriebsvorbereitenden Maßnahmen, auf die wir später detailliert eingehen werden, in die Entwicklerteams tragen, dort mitarbeiten und Betriebsgrundlagen manifestieren.

Leider ist es aber heutzutage immer noch so, dass ausgerechnet die uralte Disziplin des Loggings den Betrieb oft am wenigsten unterstützt. Folgende Probleme haben wir in den letzten Jahren immer und immer wieder aus verschiedensten Softwareteams gehört:

  • Keine aussagekräftigen Inhalte in den Logs

  • Viel zu groß, man findet die Information im Grundrauschen nicht

  • Nicht sortierbar

  • Nicht effizient indizierbar und somit

  • Nicht effizient durchsuchbar

  • Nicht oder kaum statistisch verwertbar

Aus unserer Erfahrung heraus ist es daher besonders wichtig, dass bereits in der Phase des Ramp-ups einer Anwendung abgeklärt ist, welche Anforderungen der Betrieb an Anwendungslogfiles stellt. Schließlich müssen gerade die Kollegen vom Betrieb wissen, was die Anwendung so anstellt. Wichtiger ist aber, dass Logfiles schnell und effizient auswertbar sind. Welche Voraussetzungen Entwickler hierfür einhalten müssen, werden wir später im Artikel noch detaillierter besprechen.

Aber was ist eigentlich an klassischem Logging so schwer? Das machen wir Entwickler doch schon von Beginn des Softwarezeitalters an? Nun ja, fragt man dies einen althergebrachten Systemadministrator, wird er wohl so oder so ähnlich antworten: „Gute Logfiles konnten Entwickler noch nie. WIR sorgen immer im Nachgang dafür, dass die Logfiles wenigstens ein klein wenig Aussage und so etwas wie einen vollständigen Timestamp haben. Oft bekommen wir Anwendungsarchive über den Zaun geworfen, in denen das Logging noch auf Debug-Level steht. 3 Megabyte Logeinträge pro Sekunde sind keine Seltenheit.

Was also macht ein gutes, produktionsunterstützendes Anwendung-Logging aus?

  • Loglevel im Betrieb anpassbar (darauf gehen wir in einem anderen Artikel der Serie detaillierter ein).

  • Trennung technischer Logeinträge (z. B. gefangene Exceptions) von fachlichen Informationen (z. B. fehlende Möglichkeit, ein Dokument zu drucken, da noch Informationen im Dokument fehlen). Weiterhin sollte man Informationen, die einen rein statistischen oder auditierenden Inhalt haben, ebenso separat loggen. Der Anwendungsentwickler muss sich dessen bewusst sein.

  • Um den Kollegen des Betriebs ein schnell und effizient auswertbares Log bereitzustellen, sollte der Level eines Logeintrags sehr sorgfältig gewählt werden. Eine gefangene und behandelte fachliche Exception ist sicherlich für den Betrieb kein Error-Level.

  • Damit das Logging keinen Einfluss auf die Anwendung selbst hat, sei es Performance oder Stabilität betreffend, sollte man auch hier Appender mit Bedacht auswählen, die dementsprechend arbeiten. Logeinträge, die Statistiken füttern, müssen nicht in allen Fällen zwingend ankommen und verarbeitet werden, hier reicht eventuell ein „Fire and Forget“-Ansatz. Ein Error-Log jedoch sollte unter allen Umständen sauber geschrieben werden.

  • Um sicherzustellen, dass der Betrieb eine Reihenfolge von technischen Problemen erkennen kann, ist es unabdingbar, dass Logeinträge mit einer einheitlichen, idealerweise übergreifend bereitgestellten Syntax ausgestattet sind, die Timestamps und Location beinhalten sollten. Wenn möglich, sind auch die Logmeldungen einheitlich in einer Sprache und idealerweise zur Verständigung in Englisch.

Zu guter Letzt ist es sehr praktisch, wenn man in der Lage ist, Loglevels, Appender und alle weiteren relevanten Spieler zur Laufzeit anzupassen. Hier sollte man beachten, dass eine Anwendung eventuell in einem Clusterverbund läuft und man nur einen einzelnen Knoten im Cluster in einen Debug-Zustand versetzen können möchte. Hierbei muss beachtet werden, dass die Appender dieses auch unterstützen.

Listing 1

Schlecht:  05:23:14 INFO update on Entity user
besser:    2014-01-04T14:00:39,664+0200 INFO [d.f.t.UserService:22] [7f529ac-...] Updating user 66579

Hält sich ein Team an die genannten Punkte und diskutiert die genannten Probleme, so sollte von Beginn an der Informationsgehalt in den Logs stimmen, und sie sollten ordentlich lesbar, verfolgbar und auswertbar sein.

Auf die verschiedenen Logframeworks gehen wir in diesem Artikel nicht näher ein. In diesem Heftschwerpunkt finden Sie aber weitere Beiträge, die sich mit einigen Frameworks genauer beschäftigen.

arrasz_abb2.eps_fmt1.jpgAbb. 2: Beispielhaftes Listing

Abbildung 2 zeigt ein beispielhaftes Listing, das die verschiedenen Loganforderungen aufzeigt. Man erkennt den Unterschied zwischen technischem und fachlichem Logging sowie das spezielle Logging für die Statistik. Ebenso erkennbar sind die Anforderungen an die verschiedenen Logs, manche Einträge müssen immer im Logfile auftauchen (Error), manche nur zur Detailbetrachtung (Info), und manche können sogar zeitlich flexibel geschrieben werden (Validation).

Kommen wir nun also dazu, welche Themen man für eine saubere Logkonfiguration im Auge behalten muss. Logkonfiguration ist ein Thema, das oberflächlich betrachtet tausend Mal behandelt wurde. Warum greifen wir das also nun hier doch wieder auf?

Die aktuellen Veränderungen im Aufbau von Anwendungen machen es nötig, hier einen genaueren Blick darauf zu werfen. Zuerst einmal können unbedachte Logkonfigurationen sehr einfach das I/O-Subsystem einer Architektur lahmlegen, zum anderen kann man hier mit ein paar Kniffen sehr ordentlich lesbare und somit gute Logfiles vorbereiten.

Es gibt nichts Schlimmeres, als einen wütenden Administrator vor sich stehen zu haben, der sich während eines Systemausfalls zehn Minuten durch verschiedene Logfiles wühlen musste, bis er erkannt hat, dass lediglich ein Lock auf der Datenbank die Probleme verursachte.

Ein weiteres Problem, das ein Entwicklerteam wunderbar auf die Betriebsmannschaft oder den DevOp in ihrem Team abwälzen kann, ist die Verantwortung für ein sinnvoll lesbares und strukturiertes Log. Um Tools verwenden zu können, die der Betriebsmannschaft ein effizient und schnell durchsuchbares Log bereitstellen, muss zuerst einmal das Entwicklerteam darüber nachdenken, welche Identifier wo in einem Logeintrag stehen soll(t)en, damit die Betriebsmannschaft schnelle Suchen und somit schnelles Incident-Management zur Verfügung stellen kann.

Natürlich bietet jedes der Werkzeuge zur Kumulierung unterschiedliche Vor- und Nachteile. Je nach Einsatzszenario sollte man hier genau abwägen, ob man eine steile Lernkurve gegenüber einer sehr detaillierten Suchfunktion in Kauf nehmen möchte, oder nicht.

Die Laufzeit eines Softwareprojekts spielt sicherlich auch in die Auswahl hinein. Eine steile Lernkurve und fein granulare Suchfunktion ist vielleicht nicht die beste Wahl für eine dynamische Webseitenentwicklung, die nur zur Fußballweltmeisterschaft in Brasilien gebraucht wird, ergibt aber für eine prozesssteuernde Software durchaus Sinn, um sie die nächsten fünfzehn Jahre weiter am Leben erhalten zu können.

arrasz_abb3.eps_fmt1.jpgAbb. 3: Vor- und Nachteile der Log-Handler Graylog2, Logstash und rsyslog

Im Detail wollen wir nun auf die Vor- und Nachteile von drei freien Vertretern von Log-Handlern mit der Möglichkeit zentraler Datenhaltung eingehen: Graylog2, Logstash und rsyslog (Abb. 3). Diese Auswahl inklusive Bewertung ist durchaus subjektiv, soll aber die unterschiedlichen Logging-Ansätze aufzeigen und visualisieren.

Graylog2 wurde 2010 von Lennart Koopmann begonnen, und kommerzieller Support kann durch den Schirmherr TORCH GmbH erhalten werden (Abb. 4). Graylog2 wurde und wird sehr aktiv unter Einbeziehung der entstandenen Community weiterentwickelt. Es stellt eine umfassende Logging-Lösung bereit, die mit Elasticsearch zur Speicherung und einer Weboberfläche zur Analyse der gesammelten Daten punktet.

arrasz_abb4.tif_fmt1.jpgAbb. 4: Graylog2

In einem ähnlichen Zeitrahmen ist auch Logstash entstanden – ab 2009 wurde dieses von Jordan Sissel und Pete Fritchman entwickelt, wobei auch hier die Entwicklung stetig fortschreitet. Durch die Nähe von Logstash zu Elasticsearch und Kibana geschieht dies seit 2013 im Rahmen von Elasticsearch (Abb. 5). Logstash ist im Gegensatz zu Graylog2 keine fertige Lösung, sondern eher ein flexibler Baukasten, um eine passende Lösung in Verbindung mit anderen Projekten herzustellen. Auf Kibana wird Tammo van Lessen ab Seite 48 genauer eingehen.

arrasz_abb5.tif_fmt1.jpgAbb. 5: Kibana

rsyslog ist eine syslog-Alternative von Rainer Gerhards, gesponsert von dessen Firma Adiscon GmbH (Abb. 6). Dieses Produkt ist mit Entstehungsjahr 2004 ein wenig älter als die vorherigen, wird jedoch ebenfalls noch aktiv weiterentwickelt. Durch seine Historie als syslog-Nachfolger ist rsyslog viel tiefer im System verankert und eher Systemadministratoren als Entwicklern geläufig. Durch ein Modulsystem ist es jedoch ähnlich wie Logstash eine flexible Anwendung, um Logs zu verarbeiten.

arrasz_abb6.tif_fmt1.jpgAbb. 6: rsyslog

Ein Vergleich dieser drei leicht unterschiedlichen Lösungen ergibt auf jeden Fall Sinn – eine Bewertung ist jedoch sehr schwierig und stark abhängig von Faktoren des Projekts und der allgemeinen Umgebung.

In den Einleitungen der drei vorgestellten Programme wurde schon auf einen der größten Unterschiede eingegangen: Wie „fertig“ bzw. flexibel muss die Lösung sein, wie kann sie sich in existierende Infrastruktur integrieren, wie viel Komfort ist out of the box vorhanden? Während zum Beispiel bei Graylog2 schon eine Rechteverwaltung für Benutzer und Zuordnung zu Hosts integriert ist, muss dieses bei den anderen Varianten im Nachhinein eventuell noch nachgebaut werden. Im Gegenzug sind jedoch die Ein- bzw. Ausgabeformate bei den beiden anderen Produkten viel flexibler und erlauben somit eine Anpassung an Infrastruktur, die man möglicherweise nicht komplett unter Kontrolle hat.

Struktur bringt hier besonders Graylog2 mit dem Graylog Extended Log Format (GELF). Um Nachteile eines syslog-Formats zu umgehen, das nur einzeilig, limitiert von der Größe und unstrukturiert ist, wurde für rsyslog ein strukturiertes Textformat auf Basis von JSON spezifiziert. Auf der anderen Seite hält sich rsyslog prinzipiell durch seine Vergangenheit an syslog, während Logstash mit „grok“ einen kompletten Log-Parser bereitstellt, der beliebig zwischen Formaten konvertiert.

Eine Anforderung kann der Ressourcenverbrauch während der Logsammlung auf dem Quellhost sein. Wenn die zu überwachende Applikation selbst für die Versendung der Logs verantwortlich ist, hält sich der Verbrauch in Grenzen – ein zusätzlich gestarteter Logstash Daemon zur Logsammlung aus einer Datei zieht jedoch eine JVM-Laufzeitumgebung mit JRuby nach sich und ist hierdurch schwergewichtiger als ein rsyslog Daemon, der sowieso gestartet ist. Graylog2 beschränkt sich ganz auf die Serverseite.

Wie schon angesprochen, hat auch die Projektlaufzeit bzw. die konkreten Kompetenzen der Teammitglieder Einfluss auf die Auswahl. Komplexität des Stacks kann hier gegenübergestellt werden. Die Speicherung von Logs in Plaintext-Dateien wird wohl auch in Jahrzehnten noch ohne Spezialwerkzeug möglich sein – Graylog2 ist für Elasticsearch als Speicher-Backend geschaffen worden.

Weitere benötigte „bewegliche Teile“ bei Graylog2 sind die grafische Oberfläche (derzeit eine Play-Webapplikation), eine MongoDB zur Konfiguration, die Backend-Applikation zum Logempfang bzw. zur -verarbeitung und Elasticsearch. Logstash ist hier weniger vielfältig und besteht aus einer einzigen Applikation, die unterschiedlich konfiguriert wird – die Komplexität ist hier also wählbar.

Ein Beispiel wäre eine Umgebung mit Elasticsearch und Kibana – eine JavaScript-Webanwendung zur Visualisierung von Daten in Elasticsearch – und eine/mehrere Logstash-Instanzen zur Speicherung der Logs. Auch rsyslog lässt sich für Elasticsearch konfigurieren, üblicher ist aber in diesem Umfeld die simple Speicherung von syslogs in rollenden Logs im Dateisystem.

Tipp

Fachprozesse mit einer eindeutigen Prozess-ID ausstatten und im Logeintrag immer exakt an der gleichen Stelle oder immer sehr eindeutig durch einen regulären Ausdruck auffindbar bereitstellen. Somit sind Werkzeuge wie Elasticsearch oder dergleichen sehr effizient in der Lage, die Einträge durchsuchbar zu machen und strukturiert bereitzustellen.

Voraussetzung hierfür ist natürlich, dass die Prozess-ID immer eindeutig ist, auch über verteilte Applikationskontexte hinweg (siehe beispielsweise das Stichwort MDC (=Mapped Diagnostic Contexts) im SLF4j-Umfeld).

Fazit

In diesem Teil der Serie wollten wir aufzeigen, wie wichtig eine enge Kooperation zwischen Entwicklern und Betreibern, besser ein Cross-functional Team (siehe gleichnamiger Kasten), für den Start einer Softwareentwicklung ist. Es gibt viele kleine Fallstricke, aber auch Chancen, um das gesamte Projekt effizienter und besser zu machen, die man von vorne herein im Auge behalten sollte.

Ein Entwicklerteam, das von Beginn an mit solchen Anforderungen konfrontiert ist, macht sich komplett andere und deutlich mehr Gedanken über ihre Art, Logging zu entwickeln. Wir hoffen, wir konnten die richtigen Denkanstöße und Ansätze aufzeigen.

Im kommenden Teil der Serie gehen wir detaillierter auf die konkreten Anforderungen an die Phase der Preproduktion ein. Auch hier ist eine enge Zusammenarbeit zwischen Entwicklern und Betreibern eminent wichtig, Verständnis für das Zusammenspiel des Stacks muss gegeben sein, ansonsten werden die Entwickler auch hier in der Lage sein, viele unnötige Fallstricke für den Betrieb aufzubauen.

Ausblick

In der nächsten Ausgabe werden wir uns intensiver dem Thema Produktionsvorbereitung und -stabilisierung widmen. Wie können wir unser Set-up gegen Ausfälle, Grundlast beziehungsweise Lastspitzen stabilisieren und stählen?

Cross-functional Teams

Unter einem Cross-functional Team versteht man ein Team, das aus Mitgliedern verschiedener Rollen besteht. Im Team sind Betreiber genauso wie Entwickler als auch UX-Experten integriert. Das Team löst im Konsens die anstehenden Aufgaben. Die Spezialisten im Team beraten anhand der kommenden Aufgaben, entschieden wird jedoch im Konsens. Ein Cross-functional Team besteht oft aus:

  • Juniorentwicklern

  • Seniorentwicklern

  • Architekten oder architekturerfahrenen Entwicklern

  • UX Developer (wenn benötigt)

  • DevOps/SysOps

Um dieses arbeitende Team herum braucht es, je nach Prozess, in dem gearbeitet wird, natürlich auch noch Mitarbeiter, welche die Kommunikation in die Fachabteilungen steuern und organisieren. Dies ignorieren wir an dieser Stelle eiskalt, da es den Rahmen des Artikels ansonsten sprengen würde.

arrasz_joachim_sw.tif_fmt1.jpgJoachim Arrasz ist als Software- und Systemarchitekt in Karlsruhe bei der synyx GmbH & Co. KG als Leiter der CodeClinic tätig. Darüber hinaus twittert und bloggt er gerne.

Blog Twitter

buch_jonathan_sw.tif_fmt1.jpgJonathan Buch ist als Softwareentwickler in Karlsruhe bei der ­synyx GmbH & Co. KG tätig und beschäftigt sich dort mit Entwicklung, Systemadministration und CodeClinic-Aufgaben.

Twitter
Desktop Tablet Mobile
Desktop Tablet Mobile