Archive for the ‘Software Entwicklung’ Category

konsequente Pragmatik - pragmatisches Vorgehen aber konsequente Umsetzung

Dienstag, März 11th, 2008

In der Software-Entwicklung kommt es immer wieder zur Anschuldigung, die verwendeten Prozesse wären schwergewichtigt und zäh - eine Anschuldigung die zum guten Teil richtig ist.Viele Teams verkomplizieren sich die Arbeit massiv, indem Dokumentationen erstellt werden, Meetings anberaumt werden, Entscheidungsträger definiert werden - nur “geschafft” wird wenig.

Um aus dieser Falle zu gelangen, kann Pragmatik helfen. Die schlichte Fragestellung: “Wie kann ich mein Problem am einfachsten lösen?” verhilft hierbei zur Lösung. Es geht bei einfach pragmatischem Vorgehen nicht darum, möglichst elegante Lösungsszenarien zu entwerfen oder komplexe Patterns anzuwenden - sondern einfach nur das Problem zu lösen.

Ein pragmatisches Vorgehen ist gerade im Projektgeschäft außerordentlich hilfreich, da es zumeist positiv von den Kunden aufgenommen wird, wenn man sich nicht verkünstelt, sondern schlicht das Problem auf den Punkt bringt und dazu eine Lösung anbietet.

Andererseits ist pragmatisches Vorgehen aber auch eine Gefahr! Durch die “Möglichkeit”, Änderungen schnell umzusetzen und evtl. die erste (aber nicht unbedingt beste Lösung) zu verwenden, können schnell Kurzschlußhandlungen entstehen, die einem im späteren Projektverlauf massiv das Leben schwer machen oder aber wieder Änderungen nach sich ziehen.

Den Spagat zwischen Pragmatik einerseits und der Vermeidung von Schnellschüssen andererseits stellt die “konsequente Umsetzung” dar.

Was ist darunter zu verstehen?

Ganz einfach - tritt ein Problem auf, wird pragmatisch analysiert, wie das Problem gelöst werden kann. Die gefundene Lösung wird dann aber konsequent auf ihre Tragfähigkeit analysiert. Dabei müssen alle relevanten Aspekte mit einbezogen werden (funktional wie auch nicht-funktional). Nur durch eine solche Vorgehensweise kann sichergestellt werden, dass die bestehenden Probleme einerseits gelöst werden, andererseits aber eine “Zukunftssicherung” mit einfließt.

Auf Prozessthemen angewendet bedeutet dies, dass im Rahmen einer pragmatischen Lösungsfindung die Entscheidung getroffen werden kann, eine zusätzliche Entscheidungsinstanz einzuführen. Konsequenterweise bedeutet dies aber auch Zeitaufwand, der mit eingeplant werden muss. Dabei bedeutet Planung in diesem Fall auch, dass es nicht nur eine Kostenstelle gibt, sondern im Zeitplan tatsächlich eingetragen werden muss.

Diese Konsequenz in der Umsetzung ist gerade zu Anfang, oder aber in eingeschliffenen Teams, außerordentlich schwierig. Da dort überwiegend gelebte Prozesse vorhanden sind, ist die Umsetzung natürlich ein Problem, da es hier um Veränderung bestehenden Verhaltens geht. Diese Veränderung kann nur durch stete Kontrolle und Erinnerung (nicht aber Ermahnung) einhergehen.

Insgesamt löst “konsequente Pragmatik” diverse Probleme, die vielen schwergewichtigen Prozessen zugeschrieben werden. Im Kern kommt es, wie immer, darauf an, dass kein Thema überbewertet wird, aber auch nicht vernachlässigt wird. Eine pragmatische Lösungsfindung, aber konsequente Umsetzung kann auch die Verwendung von schwergewichtigen Prozessen vereinfachen.

P.S.: Was ich natürlich nicht erwähnt habe, wenngleich es mindestens den gleichen Stellenwert hat, ist die Seite der “Betroffenen”. Diese sind verständlicherweise auch gehalten, Prozesse zu leben und dies wechselseitig zu forcieren - sprich genau das Verhalten auch von Kollegen einzufordern. Verwendet man keine konsequente wechselseitige “Ermahnung”, verwässern die Strukturen. Andererseits: Wenn Prozesse und damit möglicherweise einhergehende Verbesserungen nicht von allen Beteiligten gewollt werden, kann man sich natürlich wunderbar die Zähne daran ausbeißen, diese einzuführen/umzusetzen :)

Trennung von Support und Entwicklung 1

Sonntag, Juni 10th, 2007

Eigentlich hätte ich den Beitrag mit einer anderen Überschrift versehen soll .. z.B. “Dienstleistung - Balanceakt zwischen den Welten”, das wäre aber etwas zu theatralisch und würde ganz sicher meinem Stil nicht entsprechen.
Also versuche ich es etwas bodenständiger.

Als Dienstleister im Software-Umfeld etntwickelt man einerseits Lösungen für Kundenprobleme, andererseits kommt man aber auch um Fragen der Wartung und der Fehlerbehandlung nicht herum. Unter Wartung kann man dabei Weiterentwicklungen verstehen, aber auch Vorgespräche dazu. Unter Fehlerbehandlung verstehe ich in diesem Falle aber nicht die techn. Fehlerbehandlung, sondern eher Anfragen, die sich auf Fehler beziehen, die durch den Betrieb nicht gelöst werden können.

Typischerweise liegt es nahe, diese Fehler an die Entwickler weiterzureichen, da diese die Komponenten entwickelt haben und für die Fehlerbehebung am Besten durchführen können.
Ist man in einem überschaubaren Projekt, oder handelt es sich um Anfragen, die zu dem jeweiligen Projekt gehören, ist dies in Ordnung bzw. verständlich.
In einem Umfeld, in dem man aber mehrere verschiedene Projekte abhandelt, ist dies auf Dauer nicht tragfähig, da die anstehenden Projekte um die Zeit der Fehlerbehebung verlängert werden, oder über Mehrarbeit abgehandelt werden, was nicht wünschenswert ist.

Wie kann dies nun praktikabel gelöst werden? Verwendet man für die Problemlösung einen SixSigma Ansatz, also einen analytisch geprägten Ansatz, so benötigt man eine Ausgangssituation. In diesem Falle kann man sagen, dass das Support-Team keinerlei Anfragen bearbeitet und das Entwickler-Team alle Anfragen beantwortet. Nun ist die Aufgabe, dieses Verhältnis zu verschieben. Für einen guten Schnitt soll dieses Verhältnis auf 50/50 angehoben werden.

Was ist das grundsätzliche Problem für ein Support-Team? - Es kommen über die Zeit Anfragen der verschiedensten Art, die bearbeitet werden sollen. Diese können sich entweder auf die implementierte Lösung direkt oder das Umfeld dieser Lösung beziehen, um das Problem erstmal zu vereinfachen. Später kann es verkompliziert werden, indem auch Anfragen eher fachlicher Natur bearbeitet werden sollen.

Nachdem die Aufgabe der Definition abgeschlossen ist und damit auch der finanzielle bzw. zeitliche Impact klar ist - die unzweifelhafte Zeitersparnis für die Entwickler und die höhere Produktivität des Support-Teams - geht es daran die Informationen zu sammeln, auf Basis deren weiter Entscheidungen und konkrete Handlungsmassnahmen abgeleitet werden können.

Nun kommt die Aufgabe der Messung. In dieser müssen Daten erhoben werden, die zielführend sind und valide Aussagen darüber zulassen, welcher Art die Anfragen sind. Dazu kann ein evtl. bereits bestehendes Trouble-Ticket-System verwendet werden. Dazu ist eine Kategorisierung der Tickets notwendig. Diese sollte mehrfach vorgenommen werden, um die unterschiedlichen Dimensionen des Fehlers zu erfassen. Sinnvolle Dimensionen sind:

  • Art des Fehlers - Datenfehler, techn. Fehler, Bedienungsfehler, Mappingfehler, Programmierfehler
  • Tiefe des Fehlers - simpel, einfach, mittel, schwer
  • Umfang des Fehlers - Komponente, Datenstrecke, Randsysteme, Benutzer
  • betroffene Systeme - EAI, Randsysteme, Datenbanken

Typischerweise erhält man an dieser Stelle den Einwand, dass die ganze Datenerhebung keine Sinn macht und sowieso überflüssig ist. Man könnte meinen, dass dem so ist, stimmt aber nicht. Das Problem ist, dass man, methodisch betrachtet, etwas erreichen möchte, ohne Aufwände in Blindleistung zu investieren. Aus diesem Grunde sollte im ersten Schritt Daten erhoben werden, die Aussagen darüber zulassen, wieviel Anfragen überhaupt kommen und wie diese eingestuft werden können. Anschließend kann man für die Kategorien mit dem höchsten Aufkommen überlegen, wie diese behandelt werden können.

Und da ich jetzt keine Lust mehr habe, weiter zu schreiben, kommt morgen oder so der Rest zum Thema Analysieren und Verbessern.

Kommentare zum Bereich Definieren und Messen sind herzlich willkommen, gerade auch um andere Sichtweisen einzuarbeiten…

Dokumentation - Quelltext

Sonntag, Juni 3rd, 2007

So und weiter geht’s im Text um eine sinnvolle und für die Wartung brauchbare Dokumentation. Diesmal wechsle ich den Themenbereich und wende mich direkt den Quelltexten zu, denn aus denen sind die meisten Anwendungen dieser Tage aufgebaut.

Wenn Fehler auftreten, äußert sich das im Falle von Java zumeist durch einen Stack Trace. Dieser gibt an, in welcher Java Klasse der Fehler aufgetreten ist und wie der Aufrufgraph dahin aussieht. Darüber lässt sich nachvollziehen, über welche anderen Java-Klassen hinweg zu dieser, möglicherweise fehlerhaften, Stelle im Code gelangt worden ist.

Was passiert nun, wenn an diesen Stellen keine Fehlerbehandlung durchgeführt wird? Richtig - es werden Java Exceptions geworfen, die genau das aussagen, was gerade passiert. Übliche Beispiele wären NullPointerException, ArrayIndexOutOfBoundsException oder auch RemoteException - sehr beliebt übrigens auch aufgrund ihrer hohen Aussagekraft in einem Applikationskontext :-)

Was braucht nun der Support? Der Support oder auch die Wartungsmannschaft möchte möglichst schnell die Stelle in den Protokolldateien finden, die den Fehler erwähnt und anschließend möglichst schnell erkennen können, was der Fehler genau ist. Im Sinne einer möglichst niedrigen Ausfallzeit ist das auch Sinn der Übung. Nun hilft aber eine Darstellung der Form “RemoteException in Klasse Blah, Zeile Blub” herzlich wenig.

Darum plädiere ich ganz massiv, wie dies eigentlich auch getan werden sollte, für sprechende Exceptions, die zumindest auf einen Cluster von Fehlern hinweisen.

Ein Beispiel wären ein paar Projekte aus meinem Umfeld. Diese verwenden eine andere Komponente zur Auflösung von Qualitätsgruppen. Tritt beim Zugriff auf diese ein Fehler auf, sieht man in den Protokolldateien eine lustige RemoteException (oder auch CORBA Exception) und mehr nicht - suboptimal. Wie könnte es besser aussehen? Geholfen wäre zum Beispiel durch eine QualityCodeCacheManagerUnavailableException!

Durch solche Fehlertexte ist zwar die Lösung noch nicht gefunden, eine weitere Analyse an dieser Stelle ist aber überflüssig, weil das Problem woanders liegt. Nun kann sich aber der Support direkt dieser Thematik zuwenden und nachschlagen, was bei einem solchen Fehler zu tun ist.

Eine weitere Alternative ist die Eskalation über eMails. Dadurch können die notwendigen Informationen direkt an die Zuständigen Personen übermittelt werden (idealerweise eine Verteilerliste), ohne direktes Eingreifen zu erfordern. Dies könnte z.B. wie folgt aussehen:

Bitte legen Sie für den Qualitätscode das Wertpapier XY fest. Es wurde keine Gruppe gefunden.
Im Anschluss daran ist der Betrieb über den Neustart der Komponente zu informieren.
Diese eMail wurde automatisch generiert, bitte antworten Sie nach Abschluss der Wartungstätigkeit.

Wird diese eMail so gestaltet, dass Sie einerseits an die Verteilerliste gelangt und andererseits dem Betrieb mitgegeben wird, erkennt dieser sofort, wann kein direktes manuelles Eingreifen notwendig ist. Steht der Betrieb zudem als “Reply-To” Empfängerkreis in der eMail, kann dieser direkt informiert werden, wenn der normale Betrieb weitergehen soll.

Was ist der Nachteil einer solchen Vorgehensweise? Das ist relativ leicht dargestellt:

  • Die Java Quelltexte werden länger, da mehr “named” Exceptions geworfen werden
  • Die Quelltexte erhalten eine höhere Komplexität, da mehr defensive Prüflogiken eingebaut werden
  • Der Entwickler muss sich nicht nur darüber Gedanken machen, wie er sein Problem löst, sondern auch, wie er dem Wartungsproblem begegnet

Es gibt sicherlich noch eine Menge mehr, was an dieser Stelle aufgeführt werden kann, aber nun auch ein paar positive Anmerkungen:

  • Die Entwickler werden entlastet, da mehr Aufgaben durch den Betrieb/Support gelöst werden können
  • Die Entwickler sind nur noch dann einbezogen, wenn der Fehler nicht durch den 2nd Level gelöst werden kann. In diesem Fall handelt es sich aber um “sinnvolle” Fehler, die tatsächlich einen Entwickler erfordern. Dies ist meistens nicht der Fall
  • Die Projekte werden automatisch robuster entwickelt. Da der Entwickler möglichst wenig Aufgaben im Wartungsumfeld wahrnehmen möchte, es ihm ein Anliegen, die möglichen Fehler möglichst umfassend zu dokumentieren (in Form von Exceptions und SDs)

Was ist das Ende vom Lied? Eine bessere Supportleistung ist möglich. Dies ist in diesem Falle mit einem Eingriff in den Quelltext verbunden, der den üblichen Rattenschwanz hinsichtlich Change, Deployment und Re-Test nach sich zieht, aber schlußendlich qualtitativ höheren Code hinterlässt.

JMX - Java Management Extensions

Dienstag, Mai 29th, 2007

Hier ein paar Links zum Thema JMX für alle, die sich näher damit beschäftigen möchten:

Von den Seiten her empfehle ich für den Einstieg die Wikipedia Seite. Danach das JBoss Wiki JMX. Damit gibt es einerseits eine grobe Übersicht zum Thema Management von Java Anwendungen und andererseits den eher praktisch orientierten Teil mit Fokus JBoss. Die anderen Seiten in der Liste nähern sich dem Thema eher entwicklungslastig, sollten aber dennoch nicht übergangen werden …

Ein Problem bei der Suche ist mir aufgefallen: Es gibt relativ wenig konsistente Informationen zu dem Thema, auch wenn sehr viel und sehr breit darüber publiziert wird. Insbesondere aus Betriebsanforderungssicht her, scheinen sich wenige Leute damit zu beschäftigen, was entweder für die unglaubliche Stabilität der Plattform spricht (wie gesagt: un-glaublich!), oder aber eher von untergeordnetem Interesse zu sein scheint.

Auf jeden Fall ein Thema, mit dem man sich auseinandersetzen sollte !

Das Verhältnis zwischen Entwickler und Support…

Montag, Mai 28th, 2007

… oder wie zwei Welten aufeinander prallen! - Das wäre natürlich eine eher harsche Darstellung der Dinge, wenngleich nicht soo verkehrt :-)

Was kennzeichnet einen Entwickler ?
Wenn er ein Projekt entwickelt hat, gehört der Entwickler sicherlich zu dem Personenkreis, die die meiste Ahnung von der Materie haben. Sein Projekt, Seine Kenntnis, Sein Wissen, Sein Baby. Was aber macht ein Entwickler mit Projekten, die er überhaupt nicht kennt? - Richtig! Dumm aus der Wäsche gucken, bzw. wenn er von der pragmatischen Sorte ist, sich das Projekt beschaffen, in die Entwicklungsumgebung seines Vertrauens importieren und sich schlau machen. Danach Fragen beantworten und die Welt mit dem neu erworbenen Wissen beglücken.

Die Beschreibung ist vielleicht extrem unpassend, aber ich kenne genug Entwickler, auf die das Bild zutrifft und damit bescheinige ich dem obigen Konstrukt Objektivität :-) Für die Zwecke hier ist das auch absolut ausreichend … nun zur zweiten Person !

Was kennzeichnet den Support ?
Typischerweise hat der Support ein eher flaches Wissen über die Komponenten, die er betreut. Was bedeutet flach? - Da er eher viel zu betreuen hat und überall immer mal wieder Fehler auftauchen, kennt er Seine Projekte eher oberflächlich - aus Fehlersicht. Seine Pappenheimer kennt schließlich jeder und die Fehler Seiner Schützlinge hat man nach einer Zeit auch ganz gut herausgefunden. Dafür sieht es beim Tiefgang der Kenntnisse eher mau aus, schließlich hat man kaum Zeit für die tiefere Beschäftigung, aber man weiß, wo es steht !

Was ist beim Übergang von Entwicklung zum Support zu beachten ?
Wenn zwei Menschen sich unterhalten, die unterschiedliche Sprachen sprechen, passieren oftmals ziemlich lustige Dinge. Meistens läuft es darauf hinaus, dass es gemeinsame Sprache gesucht und gefunden wird und die Kommunikation anschließend “mit Händen und Füßen” weitergeführt wird - halt mit dem, was gerade in Reichweite ist.

Was ist die gemeinsame Sprache, in der sich Support und Entwickler unterhalten können ? - Das Phänomen, dass beiden bekannt ist und von beiden verdammt wird: DER FEHLER ! Der Fehler ist der gemeinsame Dreh- und Angelpunkt. Dem Entwickler läuft er immer wieder über den Weg und er ist stets bemüht, ihn auszumerzen, zu erschlagen, zu umschiffen oder einfach zu igorieren zu behandeln. Beim Support taucht dieser ungebetene Gast auch auf - zwar im Idealfall seltener, aber er taucht auf. Auch der Support ist bemüht, DEN FEHLER zu vertreiben, denn schließlich ist dies mitunter Teil seiner Aufgabenbeschreibung.

Was ist nun konkret zu beachten? Wenn eine Komponente aus der Entwicklung kommt, muss durchgesprochen werden, was für Fehler auftreten können. Dabei sind auch hypothetische Fehler zu besprechen, damit eine Rundumsicht erlangt wird. Dabei ist extrem wichtig, dass das Einholen von diesen Informationen nicht nur eine Bringschuld seitens der Entwickler ist, da diese meistens schon mit ihren Gedanken beim nächsten Projekt sind, sondern auch eine Holschuld des Support darstellt, da er mit der Entwicklung später klarkommen muss.
Daraus erwächst üblicherweise ein Spannungsfeld. Diese Aufzulösen ist aber relativ schwer und eigentlich ist es auch gar nicht erwünscht- Wenn die Entwickler ihre Aufgabe vollständig erledigen, ist der Support über etwaige Tätigkeiten unterrichtet und es gibt kein Problem. Wenn der Support seine Hausaufgaben nicht erledigt und aktiv nachfragt, hat er im Nachhinein Probleme und muss zwangsläufig damit klarkommen. Insofern ist es am ehesten der eigennützige Wunsch des Supports, möglichst viele Informationen aus dem Entwickler zu quetschen. Und ist dem nicht so, so liegt es im Interesse des Entwicklers, möglichst wenig vom Support zu hören - schließlich will man sich ja auch mal um andere Dinge, als die Projekte von gestern, kümmern!

Aus diesem Grunde plädiere ich für :

  • einen Support, der fragt, fragt, fragt, fragt, fragt, fragt, fragt, fragt - solange, bis er alles verstanden hat. Und dauert das zwei Tage, dann dauert das zwei Tage. Spart es eine Woche im Nachhinein: gut investiert!
  • einen Entwickler, der bereitwillig Informationen abgibt oder idealerweise diese bereits in irgendeiner Form dokumentiert. Teilt er dem Rest der Welt den Platz auch noch mit, wo das Ergebnis hinterlegt ist, sind doch eigentlich alle glücklich
  • einen Support, der alles durcharbeitet und verarbeitet, was er bekommt. Nur durch selbstständiges Lernen ist selbstständiges Wachstum möglich. Sonst landet man in der selbstverschuldeten Unmündigkeit und davon hat keiner etwas.

Also hiermit der Aufruf an alle Supporter dieser Welt: Nervt die Entwickler solange, bis ihr rausgeworfen werdet und kommt dann durch die Hintertür wieder rein und nervt weiter! Und an die Entwickler: Verübelt es ihnen nicht, sondern erduldet es mit Fassung! :-)

Dokumentation - Beschreibungen

Sonntag, Mai 27th, 2007

Aufgrund immer wieder aufkommender Diskussionen zum Thema Dokumentation in Softwareprojekten (Fokus EAI) hier mal meine Position zum Thema. Da kann man sich zwar immer gut an die eigene Nase fassen, aber notwendige Dinge werden nicht weniger notwendig, indem man nicht darüber spricht/schreibt.

Ziel einer Dokumentation ist es, eine Beschreibung für den Aufbau, die Funktionen und mögliche Fehlerquellen zu beschreiben und Gegenmassnahmen bzw. Vorgehen zu skizzieren.
Zudem sollte (evtl. mit Verweis auf entspr. Dokumente) mit aufgeführt werden, wie die Funktion aufgerufen werden muss. Das umfasst evtl. auch die Parametrisierung anderer Komponenten und externer Systeme.

Dies sollte nicht nur auf Projektebene erfolgen, sondern für jede einzelne techn. Komponente erfolgen. Neben der zentrierten Sicht auf das Projekt als solches muss dabei zwangsläufig auch die Sicht nach links bzw. rechts gewendet werden, da jede technische Komponente eingebettet ist in einen Applikationskontext.

Aus diesem Grunde sollte die Dokumentation folgermassen gegliedert sein:

  • Projektumfeld (grob)
  • betroffene Anwendungen (Beschreibung der Aufgabe, evtl. Verweis auf weitere Dokumente)
  • Datenfluss
  • Komponenten und deren Zusammenspiel untereinander

Für jede Komponente sollte eine separate Dokumentation erstellt werden. Ist dies nicht sinnvoll, sollte jeder Komponente ein separates Kapitel gewährt werden. Damit kann erreicht werden, den Stellenwert jeder einzelnen Komponente hervorzuheben und damit einen Anreiz zu bieten, mehr als nur die eben notwendigen Informationen dort abzulegen.
Es sollten folgende Fragestellungen mit einbezogen werden:

  • Welche Aufgabe erfüllt die Komponente im Gesamtkontext
  • Was für Daten werden in welchem Format (mit Abbildung) entgegengenommen
  • Was für Daten werden als Ergebnis produziert. In welcher Form geschieht dies
  • Welche Schritte vollführt die Komponente. In diesem Zusammenhang bieten sich UML Aktivitätsdiagramme an. Dieser Schritt sollte so detailliert aufgebaut sein, dass das Verhalten und die Verarbeitungslogik auch für nicht direkt im Projekt involvierte leicht nachvollziehbar ist
  • Was für Fehlerquellen sind denkbar. Wie sind diese zu identifizieren (”named” Exceptions, Protokolldateien, etc.)
  • Welche Schritte sind für Außenstehende notwendig, um Fehler zu finden und eine Lösung herbeizuführen

Ferner ist bei jeder Form von Dokumentation für Aktualität zu sorgen. Insofern ist vor jedem Deployment auf die Abnahme/Produktion zu prüfen, ob die Dokumentation angepasst werden muss und ob dies geschehen ist. Ist eine notwendige Änderung nicht durchgeführt worden, muss das Deployment verweigert werden, bis die Dokumentation aktualisiert worden ist. In notwendigen Fälle kann das Verfahren natürlich abgeändert werden.