Dienstag, November 28, 2006

Die Fehler von Microsoft

Auf der ix-Konferenz war ich heute morgen in der Session "Die Fehler von Microsoft" von Andreas Zeller (Universität des Saarlandes). Dabei ging es um die Frage, ob und wie man Fehlerhäufigkeit bestimmter Module vorhersagen kann, um diese besonders intensiv zu testen. Andreas Zeller hat dazu Untersuchungen an Microsoft- und Eclipse-Modeulen durchgeführt. Der Vortrag war nicht nur gut vorgetragen, sondern transportierte auch ein paar interessante Erkenntnisse:

  1. Wenn ein Modul in der Vergangenheit sehr fehlerträchtig war, wird es auch in Zukunft fehlerträchtig sein.

  2. Mit Metriken kann man nicht universell vorhersagen, welche Module besonders fehlerträchtig sein werden. Zitat Zeller: "Das ist ein herber Schlag für die Metrik-Community. Ein Glück, dass ich nicht dazu gehöre."

  3. Man kann je Produkt (z.B. Microsoft Internet Explorer) Metriken definieren, die ganz gut funktionieren. Dazu braucht man aber Zahlen aus der Vergangenheit. Damit ist das Verfahren nur sinnvoll für neue Module in einem bestehenden Produkt. Für die existierenden Module in einem bestehenden Produkt haben wir ja Erkenntnis Nummer 1.

  4. Die erfahrensten Entwickler machen die meisten Fehler. So hat angeblich Erich Gamma eine der höchsten Fehlerraten im Eclipse-Projekt. Und Module, die sehr viele Unittests haben, sind sehr fehleranfällig. Das liegt daran, dass die erfahrenen Entwickler immer nach vorne geschickt werden, wenn es brenzlig wird. Und die Entwickler schreiben dort viele Unittests, wo sie viele Probleme vermuten. Das bedeutet, dass die Entwickler unabhängig von Metriken eigentlich ganz gut wissen, wo die fehlerträchtigen Module rumlungern. Dann kann man sich doch auch einfach an deren Einschätzung orientieren.

Weitere Informationen zu dem Thema finden sich unter www.softevo.org.

Post bewerten

Sonntag, November 26, 2006

Gute Entwickler

Bei den XP-Days war es bei der Fishbowl-Session zu Agile 2.0 explizit ein Thema, bei anderen Vorträgen stand die Frage implizit im Raum: Wie wird man eigentlich ein guter Entwickler?
Es rief keinen Widerspruch hervor, als ich behauptet habe, die Unis würden keine nennenswerten Programmierfähigkeiten vermitteln. Ich finde das absurd: Wenn etwas im Kern aller Einzeldisziplinen der Informatik steht, dann doch wohl Programme und die muss doch auch jemand programmieren. Aber im Moment sind die Unis wohl nicht der Ort, um ein guter Programmierer zu werden. Also muss man das Programmieren wohl außerhalb der Uni lernen. Da gibt es zwei Möglichkeiten: Neben dem Studium oder nach dem Studium. Im Autismus-Mode wird das nur begrenzt gehen: Man braucht Partner, von und mit denen man lernen kann.
Da finde ich es sehr schön, dass vermehrt Lernformen auftreten, die genau das ermöglichen: Programmieren lernen.

  • Im Coding-Dojo lernt man durch Beobachten anderer Entwickler das Programmieren. Das kann mit oder ohne Pair-Programming und mit oder ohne testgetriebener Entwicklung (TDD-Dojo) geschehen.

  • Im Coding-Tournament treten Programmierpaare gegeneinander an, um Bots zu programmieren, die dann gegeneinander spielen - im Fall der XP-Days Indian Poker.


Ich habe jetzt ein paar solcher Veranstaltungen selbst mitgemacht/veranstaltet und habe erlebt, wieviel man dort in sehr kurzer Zeit lernen kann - und das mit jeder Menge Spaß. Ich halte Coding-Dojos und Coding Tournaments auch für eine Klasse Idee, um sie innerhalb von Firmen zur internen "Weiterbildung" durchzuführen.
Ein TDD-Dojo bieten übrigens Henning Wolf und ich gemeinsam auf der ix-Konferenz in Frankfurt am 30.11.06 an.

Post bewerten

NEZIAK als neue Methode der Softwareentwicklung?

Gestern haben wir bei Hennings Geburtstagsparty in ausgelassener Stimmung unsere Gedanken schweifen lassen und sind dabei auf NEZIAK gestoßen. Zu NEZIAK kommt man, wenn man KAIZEN (kontinuierliche Verbesserung in kleinen Schritten) umgedreht aufschreibt. Inhaltlich bedeutet NEZIAK entsprechend die kontinuierliche Verschlechterung in kleinen Schritten :-)
Ist natürlich offensichtlicher Blödsinn... Allerdings habe ich den Eindruck, dass viele Projekte konsequent NEZIAK einsetzen. Nanu? Wer macht denn etwas offensichtlich Blödsinniges und warum?

Post bewerten

XP-Days 2006 in Hamburg sind vorbei

Die XP-Days 2006 in Hamburg sind vorbei. Sie haben mir gut gefallen. Die Vorträge waren im wesentlichen gut bis sehr gut und ich habe alte Bekannte wieder getroffen. Schon während der Konferenz konnten die Teilnehmer bloggen. Inzwischen trudeln auf dem Konferenzblog auch die Folien zu den Vorträgen ein.

Post bewerten

Dienstag, November 21, 2006

Wie schwer kann es sein, ein PDF mit Java zu drucken?

Eigentlich ist es ganz einfach, haben wir uns gedacht. Aber nichts da. Man kann zwar mit allen möglichen Programmen PDFs erzeugen, aber die PDFs dann automatisch an einen Windows-Drucker zu schicken, scheint noch ein offenes Forschungsthema zu sein.
Unser erster Anlauf ging über die Java Printing Services. Laut API-Doku ist es ganz einfach. Man sagt mit dem PDF-Flavor, dass man ein PDF drucken will und fertig. Dummerweise hat Sun den PDF-Flavor nicht implementiert. Man hofft wohl, dass das jemand anderes tut. Wir konnten aber niemanden finden, der es auch getan hat.
Zwischenzeitlich hatten wir dann ein BAT-Programm gefunden, dass schwindelerregende Dinge mit der Registry tut. Das haben wir aber nicht zum Laufen bekommen, außerdem braucht es Admin-Zugang auf dem PC der Anwender und das ist bei Unternehmenssoftware eher nicht angesagt.
Schließlich hat uns das kommerzielle JNIWrapper aus der Klemme geholfen.
Aus dem gleichen Stall stammt übrigens auch JExplorer, mit dem man den MS-Internet-Explorer nahtlos in Swing-Anwendungen einbetten kann.

Post bewerten

Samstag, November 18, 2006

Java-Script auf dem Server

Bei aktuelllen Web-Anwendungen hat man immer Java-Script auf dem Client. Die AJAX-Frameworks versuchen, diese Tatsache zu verstecken, so dass man nur mit der einen serverseitigen Programmiersprachen arbeiten muss.
Wenn es anspruchsvoll wird, reichen die Frameworks aber nicht mehr aus und man muss doch wieder Java-Script für den Browser programmieren. Wäre es da nicht viel eleganter Java-Script auch auf dem Server einzusetzen und damit nur eine Programmiersprache benutzen zu müssen? Schließlich braucht sich Java-Script bzgl. der Sprachkonstrukte eigentlich nicht verstecken hinter anderen Script-Sprachen.
Siehe dazu Phobos.

Post bewerten

Dienstag, November 14, 2006

Unit-Testing in Multi-Projekt-Settings mit JUnit 4

Die von mir zitierte Lösung für Unit-Testing in Multi-Projekt-Settings funktioniert nur für JUnit 3.8, aber nicht für JUnit 4. Johannes Link hat die Lösung für JUnit 4 adaptiert.

Post bewerten

Dienstag, November 07, 2006

Newsfeed zieht um

Der Newsfeed zu diesem Blog wird umziehen nach: http://stefanroock.blogspot.com/rss.xml

Post bewerten

Mittwoch, November 01, 2006

Unit-Testing in Multi-Projekt-Settings

Die Eclipse-IDE bietet sich an, um ein Gesamtprojekt in mehrere Subprojekte/Komponenten zu unterteilen. Die Abhängigkeitsverwaltung in Eclipse sichert dabei, dass man keine ungewollten Abhängigkeiten in sein System einbaut.
Unverständlicherweise kann man in Eclipse aber nicht Unit-Tests über mehrere Projekte auf einmal ausführen. Wenn man sehr viele Projekte in Eclipse hat, wird das Ausführen der Unit-Tests zur echten Qual.

Aber es gibt eine ganz einfache Lösung über eine generische Test-Suite, die einfach alle Tests im Classpath ausführt. Den Code (< 100 Zeilen) dazu findet man bei Björn Martensson.

Post bewerten

Mittwoch, Oktober 11, 2006

DROP COLUMN

Wenn man agil Software entwickelt, gehören häufige Produktivreleases zum Handwerkszeug. Daraus resultieren zwangsläufig Datenmigrationen, die mehr oder weniger umfangreich bei jedem Release anfallen.

Refactorings am Code verursachen entsprechende Refactorings an den Datenbankstrukturen. Besonders häufig findet man Umbenennungen von Spalten, Typänderungen von Spalten sowie das Löschen von Spalten.

Viele Datenbanken unterstützen das Umbenennen von Spalten direkt. Dort wo es nicht geht, fügt man eine neue Spalte mit dem Zielnamen ein, kopiert die Daten von der Quell- in die Zielspalte und löscht schließlich die Quellspalte. Mit ALTER TABLE und UPDATE ist das alles auch kein Problem. Bei Typänderungen von Spalten geht man genauso vor, nur dass man zwischendurch eine temporäre Spalte einführt (sonst bekommt man einen Namenskonflikt zwischen Quell- und Zielspalte).

Das Schreiben dieser Migrationsskripte scheint erstmal sehr aufwändig und unangenehm. In unseren Projekten haben wir allerdings festgestellt, dass es dann doch nicht so schlimm ist. Auf jeden Fall ziehen wir das Schreiben der Migrationsskripte dem Hinauszögern oder Weglassen von Releases vor.

Es gibt nur ein wiederkehrendes Problem und das heißt DB2: DB2 ist anscheinend die einzige Datenbank, die Tabellenspalten nicht löschen kann.

Wir behelfen uns in diesem Fall mit temporären Tabellen: Wir legen zuerst eine Kopie der Quelltabelle an und kopieren die Daten von der Quelltabelle in die temporäre Tabelle. Dann löschen wir die Quelltabelle und legen sie mit der Zielstruktur neu an. Dann migrieren wir die Daten von der temporären Tabelle in die neue Zieltabelle (mit INSERT) und löschen schließlich die Temporärtabelle. Das ist leider aufwändig und auch fehleranfällig, weil schnell mal Indices und Fremdschlüssel-Constraints verloren gehen.

Es gibt sicher gute Gründe dafür, warum DB2 DROP COLUMN nicht unterstützt - entsprechende Argumentationen findet man beim Googlen relativ schnell. Trotzdem erschwert DB2 leider agile Softwareentwicklung deutlich mehr als die anderen relationalen Datenbanksysteme.

Post bewerten

Samstag, September 23, 2006

Video: Closures in Java

Es gibt ein ganz lustiges und informatives Video, wie Closures in Java aussehen könnten und wie sie intern auf Inner Classes abgebildet werden können.

Post bewerten

Freitag, September 22, 2006

Terminplaner in Lisp

Ich habe das Terminplaner-Beispiel zuerst in Java programmiert und dann nach Groovy (Skriptsprache für die Java-Plattform) programmiert. Das Beispiel ist in Groovy als eine der jüngsten Programmiersprachen doch erheblich kürzer und einfacher als in Java. Da hat es mich dann doch gereizt, das Beispiel auch einmal in einer der ältesten Programmiersprachen zu programmieren: Lisp. Dabei habe ich Common Lisp verwendet mit CLOS (Common Lisp Object System) und Lisp-Unit von Chris Riesbeck.

Die quantitativen Ergebnisse aller drei Implementationen zuerst einmal im Vergleich:

Java

  • 5 Fachklassen, 1 Exception-Klasse, 1 Testklasse

  • 37 Methoden inkl. Konstruktoren + 10 Methoden in Testklasse

  • 246 LOC operativ + 144 LOC für Testklasse (inkl. Leerzeilen)

  • 4 For-Schleifen, 4 If-Abfragen


Groovy

  • 4 Fachklassen, 1 Exception-Klasse, 1 Testklasse

  • 30 Methoden inkl. Konstruktoren + 9 Methoden in Testklasse

  • 203 LOC operativ + 123 LOC für Testklasse (inkl. Leerzeilen)

  • Alle 4 For-Schleifen der Java-Lösung wurden durch Closures ersetzt, die 4 If-Abfragen blieben bestehen.


Common Lisp

  • 4 Fachklassen, 1 Testklasse - Exceptions werden mit Hilfe von Conditions modelliert (nur eine Zeile notwendig)

  • 17 Methoden, 1 Condition-Funktion, 10 Testmethoden

  • 76 LoC operativ, 100 LoC Test (inkl. Leerzeilen)

  • Alle 4 Schleifen der Java-Lösung wurden durch Closures ersetzt, die 4 If-Abfragen blieben bestehen, allerdings in den spezialisierten Varianten when und unless.


Wow! Die Common-Lisp-Variante hat erheblich weniger Code als die Java- oder die Groovy-Variante. Woran liegt das?
Naheliegend wäre es, die Ursache bei dem Lisp-Feature zu suchen, dass keine andere Programmiersprache anbietet: Macros (Vorsicht: Lisp-Makros sind ganz anders als die berüchtigten C-Makros). Dem ist aber nicht so. Tatsächlich habe ich in dem Lisp-Code kein eigenes Makro selbst definiert und nur an einer Stelle von der Mächtigkeit der
Lisp-Makros profitiert. Mit assert-error aus Lisp-Unit kann man sehr einfach prüfen, ob eine Exception (im Lisp-Jargon Condition) geworfen wird:


(define-test benutzer-nicht-eingeladen-exception
(setup)
(let ((termin (make-termin stefans-kalender ein-datum 180 "TDD-Dojo")))
(assert-error 'benutzer-nicht-eingeladen (lehne-termin-ab termin "Henning"))))


Zum Vergleich der entsprechende Java-Code:


public void testBenutzerNichtEingeladenException() {
Termin termin = _stefansKalender.newTermin(_jetzt, 180, "TDD-Dojo");
try {
termin.lehneTerminAb(HENNING);
fail("BenutzerNichtVorhandenException erwartet");
} catch (BenutzerNichtEingeladenException e) {
assertTrue("Exception erwartet", true);
}
}


Das erklärt aber nicht, warum der operative Code in Lisp so viel kürzer ist als in Java oder Groovy. Eine nähere Analyse fördert folgende Gründe zu Tage:
  • In Java und Groovy werden eigene Zeilen spendiert, für schließende geschweifte Klammern. Für das Lisp-Äquivalent (schließende runde Klammern) werden keine eigenen Zeilen spendiert. Dierk König schlägt in seinem kommenden Groovy-Buch diese Art der Formatierung für Groovy für bestimmte Situationen auch vor (bei den Buildern).

    • In Java und Groovy ist es üblich, Leerzeilen in Methoden einzufügen, teilweise auch zwischen Attributen. Beides macht man in Lisp eher nicht.

    • Das aufschreiben von Attributen einer Klasse ist in Common-Lisp schlanker als in Groovy oder Java. Insbesondere gibt es prägnante Abkürzungen, um Setter und Getter und Defaultwerte zu definieren.

    • Einige Implementierungen lassen sich nicht sinnvoll 1:1 nach Common-Lisp transferieren. Daher vergleicht man ein Stück weit dann doch Apfelsinen mit Orangen (so groß wie zwischen Äpfel und Birnen sind die Unterschiede dann doch nicht :-)


    Der gewaltige Unterschied in den LoC findet sich bei der Menge der Syntaxelemente in deutlich reduzierter Form. So spart man sich in Common-Lisp zwar Einiges an Zeilen für die Attributdefinitionen in Klassen, es gibt aber die gleiche Anzahl von Attributdeklarationen. In diesem Sinne ist die Lisp-Lösung zwar kürzer als die Lösungen in Java und Groovy. Sie ist bzgl. der Komplexität aber äquivalent zur Groovy-Lösung und diese beiden Lösungen sind weniger komplex als die Java-Lösung.

    Wieviel wirkt der große Unterschied in den LoC? Quelltext wird viel häufiger gelesen als geschrieben. Daher ist die Einsparung der Tastenanschläge bei der Code-Erstellung nicht wirklich von Interesse. Wenn man allerdings beim Lesen von Quelltext weder vertikal noch horizontal scrollen muss, erleichtert dies das Lesen: Im Lisp-Terminplaner passt jede operative Klasse problemlos auf eine Bildschirmseite, so dass man jede Klasse auf einen Blick erfassen kann. Das kann man als (leichten) Vorteil von Lisp werten. Allerdings muss ich zugeben, dass man den Groovy-Code an der einen oder anderen Stelle noch etwas eleganter Formulieren kann und dann auch noch etwas an LoC einsparen kann.

    Quelltext des Terminplaners in Common-Lisp.

    Post bewerten

  • Dienstag, September 19, 2006

    Refactoring und Closures

    Refactoring-schwaches Java
    Vor wenigen Tagen schrieb ich zusammen mit Henning Wolf Beispielcode für einen Sudoku-Solver. Wir wollten damit bestimmte Aspekte testgetriebener Entwicklung (TDD) sowie von Refactoring zeigen. Dabei haben wir unter anderem folgenden Code geschrieben:


    public class Sudoku {

    final static int groesse = 9;
    private Zelle[][] _sudokuArray = new Zelle[groesse][groesse];

    public Sudoku(int[][] array) {
    for (int i = 0; i < array.length; i++) {
    for (int j = 0; j < array[i].length; j++) {
    _sudokuArray[i][j] = new Zelle(array[i][j]);
    }
    }
    }

    public String[][] gibAusgefuellt() {
    String[][] result = new String[groesse][groesse];
    for (int i = 0; i < result.length; i++) {
    for (int j = 0; j < result[i].length; j++) {
    result[i][j] = _sudokuArray[i][j].toString();
    }
    }
    return result;
    }

    ...
    }



    Hier hat man offensichtlich das DRY-Prinzip verletzt (DRY = Don't Repeat Yourself): Die zwei ineinander geschachtelten FOR-Schleifen existieren zweimal (wenn man sich den kompletten Quellcode des Sudoku-Solvers ansieht, kommt das Konstrukt sogar noch häufiger vor). Ähnliche Duplizierungen in Zusammenhang mit If-Abfragen, For- und While-Schleifen finden sich in jedem größeren Java-Programm, dass ich bisher gesehen habe.

    Prinzipiell kann man diese Code-Duplizierungen auf verschiedene Arten beseitigen. Die naheliegendste Lösung besteht im Einführen eines Interfaces MatrixBesucher:


    interfaces MatrixBesucher {
    void besucheZelle (Object[][] matrix, int i, int j)
    }



    Ein Objekt dieses Interfaces reicht man als Parameter in eine Hilfemethode iteriereMatrix:


    private static void iteriereMatrix (ZellenBesucher besucher) {
    for (int i = 0; i < groesse; i++) {
    for (int j = 0; j < groesse; j++) {
    besucher.besucheZelle(i, j);
    }
    }
    }



    Dann wird aus dem Anfangs gezeigten Code:


    public class Sudoku {

    final static int groesse = 9;
    private Zelle[][] _sudokuArray = new Zelle[groesse][groesse];

    public Sudoku(final int[][] array) {
    iteriereMatrix(new ZellenBesucher() {
    public void besucheZelle (int i, int j) {
    _sudokuArray[i][j] = new Zelle(array[i][j]);
    }
    }
    }

    public String[][] gibAusgefuellt() {
    String[][] result = new String[groesse][groesse];
    iteriereMatrix(new ZellenBesucher() {
    public void besucheZelle (int i, int j) {
    result[i][j] = _sudokuArray[i][j].toString();
    }
    }
    return result;
    }

    ...
    }



    Damit ist DRY wieder hergestellt. Das Problem daran ist nur, dass sowas kein Mensch macht. Schließlich ist die Lösung länger (mit Hilfsmethode und Interface 26 statt 16 Codezeilen) und besser lesbar ist sie leider auch nicht wirklich.

    Möglicherweise schwerer wiegt, dass man für das Refactoring in Richtung DRY die Ebene wechseln musste. Das DRY-Prinzip war innerhalb einer Klasse auf Algorithmus-Ebene verletzt und wir mussten ein neues Interface einführen, also auf die Entwurfsebene wechseln. Das bedeutet, dass der Refactoringprozess an dieser Stelle nicht-linear verlaufen ist (linear: kleines Problem, kleine Lösung; nicht-linear: kleines Problem, umständliche Lösung).

    Anmerkung: Man kann sich andere Lösungen des Problems vorstellen, die ohne die umständlichen und schwer lesbaren anonymen Inner-Classes auskommen. Solche Lösungen erfordern aber deutlich mehr Entwurfsarbeit, mitunter sogar Vererbung oder den Einsatz von Entwurfsmustern. Damit würde der Refactoring-Prozess sogar noch nicht-linearer.

    Refactoring mit Closures
    Mit Closures hingegen ließe sich das DRY-Prinzip mit wenig Aufwand umsetzen und man kann beim Refactoring auf der Algorithmus-Ebene bleiben. Zu allem Überfluss ist die Lösung auch noch leicht lesbar. Hätte Java Closures, könnte die Lösung in etwa so aussehen (die Syntax für Closures ist hier an Groovy angelehnt):


    public class Sudoku {

    final static int groesse = 9;
    private Zelle[][] _sudokuArray = new Zelle[groesse][groesse];

    public Sudoku(final int[][] array) {
    iteriereMatrix({i, j -> _sudokuArray[i][j] = new Zelle(array[i][j])};
    }

    public String[][] gibAusgefuellt() {
    String[][] result = new String[groesse][groesse];
    iteriereMatrix({i, j -> result[i][j] = _sudokuArray[i][j].toString()};
    return result;
    }

    private static void iteriereMatrix (Closure closure) {
    for (int i = 0; i < groesse; i++) {
    for (int j = 0; j < groesse; j++) {
    closure.execute(i, j);
    }
    }
    }

    ...
    }



    Und schon ist die Lösung nur noch 15 Codezeilen lang (im Gegensatz zu 16 Codezeilen beim Original-Quelltext).

    Nun kann man natürlich einwenden, dass die Closures prinzipiell auch nicht mächtiger sind als anonyme Inner-Classes, es sich hier also lediglich um Syntactic-Sugar handelt. Das ist richtig und zeigt, wie wichtig eine prägnante Syntax ist. Denn die Inner-Class-Lösung wird in der Praxis so gut wie nicht eingesetzt, während die Closure-Lösung überaus üblich ist in Programmiersprachen, die Closures unterstützen wie z.B. Lisp, Python der Groovy.

    Closures in Java
    Wenn Closures so nützlich sind und konzeptionell eigentlich nur Syntactic-Sugar für anonyme Inner-Classes darstellen, dann sollte es ja eigentlich auch kein Problem sein, Closures auch in Java zu unterstützen. Und tatsächlich gibt es Anzeichen dafür, dass wir irgendwann Closures auch in Java haben werden:

    http://article.gmane.org/gmane.comp.lang.lightweight/2274

    Interessant ist hier die Argumentation: Es ist ein grundlegendes Design-Prinzip von Java, dass nur dann Objekte auf dem Heap allokiert werden, wenn der Programmierer dies explizit anfordert (typischerweise durch new). Bei Closures muss man aber implizit Speicher auf dem Heap allokieren und daher passen Closures nicht zum Design von Java.
    Nun bricht aber seit Java 5 das Auto-Boxing dieses Prinzip und daher sei es jetzt sowieso egal und man könnte dann auch noch Closures einführen :-)

    Prinzipiell bin ich persönlich der Meinung, dass Closures mir das Leben als Java-Entwickler erleichtern würden. Gleichzeitig müsste man aber große Teile des JDKs komplett umbauen. Sonst startet der ganze Ansatz als Tiger und landet als Bettvorleger. Wenn man schon Closures hat, wird man auch erwarten, dass mind. die Collections massiv davon Gebrauch machen (z.B. für das Iterieren über die Elemente). Wo man sich sonst noch die Verwendung von Closures wünschen würde, kann man gut am GDK (Groovy Development Kit) sehen.

    Und wenn man soweit geht, dann sollte man vielleicht lieber Java als Sprache auf Deprecated setzen und die Migration nach Groovy pushen. Denn da werden Closures von Beginn an unterstützt und auch entsprechende Libraries im GDK sind verfügbar.

    Post bewerten

    Montag, September 18, 2006

    Groovy und Grails auf Konferenzen

    Eindrücke aus erster Hand zu Groovy und Grails kann man sich auf verschiedenen Konferenzen in den nächsten Monaten besorgen:

    Post bewerten

    Grails: Schnell mal eine Web-Anwendung mit Groovy für die Java-Plattform

    An anderer Stelle habe ich bereits Groovy kurz beleuchtet, die standardisierte Skriptsprache für die Java-Plattform.

    Jetzt, wo man eine so mächtige und flexible Skriptsprache hat, lag es natürlich nahe, den Rails-Ansatz auch für Groovy nutzbar zu machen. Herausgekommen ist Grails.

    Grails existiert erst in der Version 0.2.2, hat aber bereits einen erstaunlichen Entwicklungsstand. Mit wenigen Clicks ist eine erste Version der Webanwendung zusammengebaut, die man dann explorativ weiterentwickeln kann.

    Die existierende Dokumentation reicht für erste Schritte aus, vieles kann man sich durch nachdenken erschließen.

    Grails ist sicherlich eine sehr interessante Technologie für die Web-Projekte, die für die Java-Plattform entwickeln müssen/wollen. Die Java-ähnliche Syntax von Groovy erleichtert Java-Entwicklern den schnellen Einstieg.

    Post bewerten

    Sonntag, September 03, 2006

    Kommentarfunktion in diesem Blog jetzt für alle

    jedenfalls für alle mit einem Blogger-Account. Bisher musste man zusätzlich Geheimwissen mitbringen: Man musste auf das # am Ende eines Eintrages klicken, um den Eintrag einzeln zu öffnen und dort konnte man dann einen Kommentar hinterlassen. Ich habe jetzt das Template für diesen Blog so geändert, dann man die Kommentarfunktion jetzt direkt am Eintrag aufrufen kann. Außerdem habe ich das kryptische # durch "Permanent Link" ersetzt.

    Dass man zum Kommentar hinterlassen einen Blogger-Account haben muss, ist ärgerlich, aber wg. der Spam-Problematik zur leider wohl unvermeidlich.

    Post bewerten

    Donnerstag, August 24, 2006

    IDEs und der K(r)ampf zwischen Statik und Dynamik

    Für Java existieren heute mit Eclipse, IntelliJ IDEA und Konsorten sehr mächtige Entwicklungsumgebungen. Cross-Referencing, Refactoring und Auto-Completion sind Features, die man nicht mehr missen möchte.
    Dass diese Features für die aktuellen Skriptsprachen a la Python, Ruby oder Groovy nicht oder nur eingeschränkt existieren, wird häufig als Argument gegen diese Skriptsprachen verwendet.

    Aber wird über diese Features wirklich reflektiert?

    Cross-Referencing
    Mit den Cross-Referencing-Möglichkeiten der IDE kann man auf Tastendruck oder Mausclick von einer Codestelle zum referenzierten Element gelangen (z.B. von einer Variablendeklaration zur Klasse, von deren Typ die Variable ist).

    Natürlich sind die Cross-Referencing-Möglichkeiten in den IDEs deutlich mächtiger als eine Textsuche über Dateien. Aber ist der Unterschied wirklich so groß? Und ist die Textsuche häufig nicht sogar schneller?

    Refactoring
    Refactoring ist eine der großen Errungenschaften in der Neuzeit der Softwareentwicklung und ihr Automatisierungsgrad ist wirklich erstaunlich hoch. Aber welche automatisierten Refactorings nutzen wir überhaupt bei der täglichen Arbeit und wie häufig? Viele Entwickler verzichten sogar absichtlich auf bestimmte einfache Automatisierungen (z.B. "Introduce Variable"), weil sie von Hand schneller sind - die Mächtigkeit der IDEs führt bei großen Projekten leider dazu, dass die Arbeit mit ihnen mitunter doch etwas zäh wird.
    Viele Refactorings kann man in der Tat mit vertretbarem Aufwand und Risiko auch von Hand durchführen. Einige andere (z.B. "Rename Class") lassen sich auch auf anderem Wege automatisieren (Find&Replace über Dateien). Natürlich kann man sich dann oft nicht 100%ig sicher sein, dass alles korrekt geändert wurde. Man muss anschließend die Tests ausführen. Dass muss man in Java aber auch, weil es immer mehr untypisierte Referenzen in XML-Dateien (Struts, Spring, EJB etc.) gibt, die den IDEs auch mal durch die Lappen gehen.

    Auto-Completion
    Bei der automatischen Vervollständigung tippt man nur den Beginn eines Wortes ein und die IDE ergänzt die fehlenden Zeichen. Dadurch spart man Tippzeit, reduziert die Wahrscheinlichkeit von Tippfehlern und muss sich nur an den Anfang von Methodennamen erinnern.
    Interessanterweise gibt es auch in programmiersprachen-unabhängigen Editoren wie Emacs oder JEdit Auto-Completion. Dabei werden viel einfachere Verfahren eingesetzt als in den Java-IDEs, die aber erstaunlich gute Ergebnisse liefern. Ein ganz einfacher Ansatz besteht z.B. darin, bei der Auto-Completion nur die Wörter zu berücksichtigen, die in der aktuellen Datei schon mal verwendet wurden. Etwas umfangreicher ist der Ansatz, die Wörter aller Dateien eines Projektes zu verwenden.
    Ähnlich wie beim Cross-Referencing sind diese Auto-Completion-Features der Editoren qualitativ denen der IDEs unterlegen. Aber wie beim Refactoring sie sind schneller.

    Und das ist ein Faktor, den man nicht unterschätzen sollte. Ich ertappe mich beim Java-Programmieren jedenfalls immer wieder dabei, dass ich Namen komplett manuell eintippe, weil ich damit schneller bin als die zäh reagierende Entwicklungsumgebung. Und wenn ich in einem einfachen Editor eine Skriptsprache programmiere, genieße ich es, dass der Editor immer sofort reagiert. Die IDEs sind nur Bruchteile von Sekunden langsamer, aber das reicht schon aus, um den Flow beim Programmieren zu beeinträchtigen.

    Post bewerten

    Samstag, August 19, 2006

    Closures in Common Lisp

    Martin Fowler published an online article about closures. He used the Ruby programming language for the examples. There are translations of the examples to Python and a language called Boo.

    As a programming task for myself I did the examples in Common Lisp, which supported Closured already decades ago. A real lisper might be able to write the code in a more elegant way but I think the principle should become clear.

    I didn't use the Common Lisp Object System (CLOS) since for this simple example an ad-hoc modeling with hashes is simpler.


    ;; Ruby
    ; def managers(emps)
    ; return emps.select {|e| e.isManager}
    ; end

    ;; Common Lisp
    (defun is-manager (emp) (getf emp :is-manager))

    (defun managers (emps)
    (remove-if-not (lambda (emp)
    (when (is-manager emp) emp))
    emps))


    ;; Ruby
    ; def highPaid(emps)
    ; threshold = 150
    ; return emps.select {|e| e.salary > threshold}
    ; end

    ;; Common Lisp
    (defun high-paid (emps)
    (let ((threshold 150))
    (remove-if-not (lambda (emp)
    (when (> (getf emp :salary) threshold) emp))
    emps)))


    ;; Ruby
    ; def paidMore(amount)
    ; return Proc.new {|e| e.salary > amount}
    ; end

    ;; Common Lisp
    (defun paid-more (amount)
    (lambda (emp) (when (> (getf emp :salary) amount) emp)))

    ;; Ruby
    ; highPaid = paidMore(150)
    ; john = Employee.new
    ; john.salary = 200
    ; print highPaid.call(john)

    ;; Common Lisp
    (let ((high-paid (paid-more 150))
    (john '(:name John :is-manager nil :salary 200)))
    (princ (funcall high-paid john)))


    ;; Tests
    (defparameter manager-list
    '((:name Stefan :is-manager nil :salary 150)
    (:name Henning :is-manager t :salary 151)
    (:name Martin :is-manager nil :salary 120)
    (:name Christian :is-manager t :salary 200)))

    (princ #\newline)
    (princ "Test function managers")
    (princ #\newline)
    (princ (managers manager-list))
    (princ #\newline)

    (princ #\newline)
    (princ "Test function high-paid")
    (princ #\newline)
    (princ (high-paid manager-list))
    (princ #\newline)

    Post bewerten

    Freitag, August 04, 2006

    Sensing Variables for Refactorings

    Michael Feathers hat ein Konzept namens Sensing Variables beschrieben, mit dem sich Refactorings an Methoden sicherer durchführen lassen. Ein häufiges Problem mit dem Refactoring "Extract Method" besteht darin, dass der selektierte Code-Block sich nicht automatisch in eine Methode verschieben lässt (z.B. weil die neue Methode dann mehrere Rückgabewerte haben müsste). Also muss man erstmal manuell die Methode manipulieren, bevor man "Extract Method" ausführen kann. Dazu muss man häufig die Reihenfolge von Anweisungen in der Methode ändern, kann aber nur schwer feststellen, ob sich durch das Verschieben die Semantik der Methode ändert. Sensing Variables helfen, an dieser Stelle mehr Sicherheit zu bekommen.

    Post bewerten

    DSL: Domain Specific Languages

    Martin Fowler hat einen kurzen Artikel über DSLs in seinem Blog veröffentlicht. In dem Artikel erklärt er den Unterschied zwischen General Purpose Languages (GPL) und DSLs. Außerdem argumentiert Fowler, dass der Übergang zwischen APIs und DSLs fließend ist. Das API einer Bibiothek könne durchaus vergleichbar sein mit einer DSL.

    Das finde ich sehr überzeugend, vor allem wenn man sich die dynamischen Skriptsprachen a la Ruby, Groovy oder Lisp ansieht. Dort wo in Java eigene DSLs für Build-Skripte (ANT), Datenbankabfragen (Hibernate Query Language, HQL) oder Oberflächenbeschreibung (HTML, JSP) verwendet werden, haben Ruby und Konsorten einfach nur Bibiotheken, die innerhalb der Programmiersprache verwendet werden.

    Interessant finde ich, dass alle Artikel zum Thema DSL, die ich kenne (ich gebe zu, dass das nicht allzu viele sind), sich ausschließlich um Technologie-Domänen kümmern. Es kommen immer wieder dieselben technischen Beispiele für DSLs: SQL, ANT, etc. Das finde ich schade. Schließlich sind die technischen Aspekte in einem Softwareprojekt eher uninteressant im Gegensatz zu den fachlichen. DSLs nur für technische Aufgaben zu verwenden, riecht nach einer Optimierung an der falschen Stelle (wenn ich in einem Bereich 50% Aufwände spare, der nur wenige Prozent meiner Gesamtaufwände ausmacht, ist der Gesamtgewinn marginal).

    Eigentlich müssten wir nach fachlichen DSLs suchen. Interessiert das Niemanden, ist das so schwer oder lese ich einfach nur die falschen Quellen?

    Post bewerten

    Freitag, Juli 28, 2006

    Flow - Softwareentwicklung im Fluss

    Wenn ich heutige Java-Projekte sehe, dann ertappe ich mich immer wieder bei derselben Frage: "Muss das alles so schwerfällig sein?" Um dieser Frage nachzugehen, habe ich mich selbst gefragt, wie ich mir Softwareentwicklung vorstelle. Dazu fällt mir zuerst ein Wort ein: Flow

    Meine Gedanken dazu habe ich in einem Online-Artikel niedergeschrieben.

    Post bewerten

    Sonntag, Juli 23, 2006

    YouOS: Bye, bye Betriebssystem?

    YouOS ist ein webbasiertes Betriebssystem mit allerhand Anwendungen. Das ganze Ding ist noch im Alpha-Stadium, aber die Richtung ist schon mal interessant:

    • Keine Installation von Software auf dem eigenen Rechner.
    • Zugang zu den eigenen Programmen und Daten von jedem Rechner der Welt aus.
    • Automatische Datensicherung
    • Zentrale Sicherheitsmechanismen gegen Viren und andere Angriffe

    Eigentlich ist das Ganze eine naheliegende Idee. Mit Writeboards, Writely, GMail, NumSum, Flickr und anderen sind längst mehr Funktionen im Internet verfügbar, als der durchschnittliche Anwender benötigt. Was bisher fehlte, war die Integration. Man musste mehrere Accounts verwalten, sich URLs merken und konnte schlecht übergreifend über die Systeme arbeiten.

    YouOS leistet das noch nicht vollständig, aber das Potenzial ist da.

    Post bewerten

    Dienstag, Juli 18, 2006

    Buch: Hackers and Painters

    Ich habe gerade das Buch "Hackers and Painters" von Paul Graham durchgelesen. In dem Buch ist eine Reihe von Essays veröffentlicht, die (fast?) alle auch online auf auf der Web-Site von Paul Graham verfügbar sind. Trotzdem lohnt sich das Buch, um es in der Bahn oder im Urlaub zu lesen.

    Die Essays decken verschiedene Themenbereiche ab begonnen vom typischen Hacker-Charakter über Innovationen und Startups in der IT bis hin zum Programmiersprachenentwurf. Dabei vertritt Paul Graham häufig ungewöhnliche Ansichten und Ideen und regt damit zum Denken außerhalb der gängigen Bahnen an (warum die nächste Webanwendung nicht in Lisp schreiben?).

    Mir hat das Buch jedenfalls sehr gut gefallen.

    Post bewerten

    Dienstag, Juli 11, 2006

    Verantwortung in der Softwareentwicklung

    Ich habe zusammen mit Henning Wolf einen Artikel über Berufsethos und Verantwortung in der Softwareentwicklung im Java-Magazin veröffentlicht. Der Artikel ist online verfügbar.

    Der Artikel ist kontroverser als der Titel vielleicht vermuten lässt. Die drei Hauptthesen des Artikels sind:
    1. Jeder ist verantwortlich für alles, was er tut.
    2. Jeder ist verantwortlich für alles, was er denkt.
    3. Jeder ist verantwortlich für alles, was mit ihm geschieht.

    Wer würde das schon einfach so unterschreiben? Wer nicht, sollte den Artikel lesen.

    Post bewerten

    Mittwoch, Juli 05, 2006

    Regeln vs. Eigenverantwortlichkeit in agilen Projekten

    Bei den agilen Methoden gibt es deutliche Unterschiede in den Vorgaben und Regeln, die sie definieren. So ist z.B. Feature-Driven-Development sehr strikt bzgl. Rollen und Verantwortlichkeiten und eXtreme Programming definiert den Entwicklungsprozess sehr detailliert. Auf der anderen Seiten steht Scrum, dass nur grob regelt, wie die Anforderungen in das Projekt eingebracht werden. Die restliche Ausgestaltung des Projektes obliegt den Entwicklern.

    Was ist das bessere Modell? Wieviel Freiheit brauchen die Entwickler, um höchste Produktivität zu erreichen und wieviel Regeln muss man definieren, damit das Projekt nicht im Chaos versinkt?

    Vielleicht hilft bei der Beantwortung dieser Frage das Dreifus-Modell der Qualifikationsaneignung (Skill Acquisition). Demnach brauchen Anfänger Regeln und Vorgaben. Bei der Arbeit in dem so vorgegebenen Rahmen entwickelt sich Erfahrung und Intuition, so dass die Regeln und Vorgaben immer weniger wichtig werden und sogar behindern können. Also wären Feature-Driven-Development und eXtreme Programming eher für Neulinge geeignet und Scrum für erfahrene Entwickler?

    Post bewerten

    Dienstag, Juni 20, 2006

    XP-Days 2006 in Hamburg


    In diesem Jahr finden die XP-Days in Hamburg statt. Sie werden dieses Jahr zusammen von Andrena und it-agile ausgerichtet. Nähere Infos zum Einreichen von Beiträgen gibt es unter http://www.xpdays.de.

    Post bewerten

    Samstag, Juni 17, 2006

    Korrektur zu GroUnit: JUnit ohne Bytecode

    Dierk König wies mich darauf hin, dass mein erstes Argument für GroUnit im Gegensatz zu JUnit so nicht stimmt . Mit groovy.util.AllTestSuite kann man sehr wohl in JUnit auch direkt Groovy-Quellcode testen, ohne diesen vorher nach Bytecode zu compilieren.
    Vielen Dank an Dierk für die Klarstellung.

    Post bewerten

    Sonntag, Juni 11, 2006

    GroUnit: Unittests mit Groovy


    Ursprünglich als reine Fingerübung gedacht, habe ich ein Unittest-Tool für Groovy geschrieben: GroUnit. Das ist nicht weiter schwer, weil Groovy bereits Unterstützung für Unit-Tests mitbringt, allerdings ohne UI. Man kann wg. der nahtlosen Groovy-Java-Integration JUnit auch für Groovy verwenden (siehe z.B. Groovy-Web). Das hat aber ein paar Nachteile:

    • Man muss die Groovy-Klassen nach Bytecode compilieren. Für Produktionscode ist das OK, aber während der Entwicklung verlängert es unnötig die Turn-Around-Zeiten.

    • Wenn ein Test fehlschlägt, bekommt man im Stack-Trace auch die ganzen Core-Reflection-Geschichten angezeigt, die Groovy im Hintergrund durchführt. Dadurch muss man immer erst mal eine Weile im Stacktrace suchen, bis man das eigentliche Problem überhaupt gefunden hat.

    • Seit JUnit 4.0 bringt JUnit keine eigene Benutzungsoberfläche mehr mit. Diese wird von den Entwicklungsumgebungen gestellt. Das ist für Jave wunderbar. Es erzwingt für Groovy aber, dass man eine schwergewichtige Java-Entwicklungsumgebung verwendet. Häufig wäre man mit einem mächtigen Editor besser bedient.


    Ich habe versucht, in GroUnit diese Probleme zu adressieren. Sehr weit bin ich in der ersten Version 0.1 sicher noch nicht gekommen. Aber vielleicht engagieren sich noch weitere Leute für GroUnit und es wird noch was richtig Gutes.
    Zur GroUnit-Homepage mit Download-Möglichkeit.

    Post bewerten

    Freitag, Juni 09, 2006

    Groovy im Vergleich zu Java am Terminplaner-Beispiel

    Ich habe den Terminplaner, den ich als Beispiel für testgetriebene Entwicklung programmiert hatte, von Java auf Groovy migriert. Für den Terminplaner in Java hatte ich testgetrieben ca. 180 Minuten benötigt. Für die Migration nach Groovy habe ich dann ca. 60 Minuten investiert.

    Der erste Unterschied der Groovy-Lösung zur Java-Lösung ist der Wegfall der Klasse TeilnahmeStatus (war Enum bei Java). Die Teilnahme-Status-Informationen landen bei Groovy einfach in der Klasse Teilnahme.

    Die equals- und compareTo-Methoden sind in Groovy einfacher zu implementieren, weil es für beides eigene Operatoren (== und <=>) gibt, die mit Null-Werten umgehen können.

    Bei einer der compareTo-Methoden habe ich bei der Migrationen einen Fehler gefunden, der im Groovy-Code sofort offensichtlich wird. Im Java-Code kann man den Fehler durch die Klammerung beim flüchtigen Lesen übersehen (ist mir beim Schreiben der Java-Lösung ja offensichtlich auch passiert).

    Die betroffene Java-Zeile sieht so aus:

    int startZeitCompare = startZeit.compareTo(startZeit);

    In Groovy wird der Problem sofort offensichtlich:

    int startZeitCompare = startZeit <=> startZeit

    Es muss natürlich heißen:

    int startZeitCompare = startZeit <=> o.startZeit

    Die Zahlen nach der Umstellung lesen sich so:

    Java-Zahlen
    • 5 Fachklassen, 1 Exception-Klasse, 1 Testklasse
    • 37 Methoden inkl. Konstruktoren + 10 Methoden in Testklasse
    • 246 LOC operativ + 144 LOC für Testklasse (inkl. Leerzeilen)
    • 4 For-Schleifen, 4-If-Abfragen


    Groovy-Zahlen
    • 4 Fachklassen, 1 Exception-Klasse, 1 Testklasse
    • 30 Methoden inkl. Konstruktoren + 9 Methoden in Testklasse
    • 203 LOC operativ + 123 LOC für Testklasse (inkl. Leerzeilen)
    • Alle 4 For-Schleifen wurden durch Closures ersetzt, die 4-If-Abfragen blieben bestehen.


    Die Code-Ersparnis lässt sich im Wesentlichen auf folgende Groovy-Konzepte zurückführen:
    • Closures machen For-Schleifen überflüssig und sind kürzer aufzuschreiben.
    • Durch Properties werden Getter und Setter überflüssig.
    • Typecasts entfallen.
    • In den Tests spart die Uniformität von Arrays und Collections Konvertierungen.


    In Groovy habe ich also ca. 80% der LOC (Lines of Code) benötigt, die ich für die Java-Lösung benötigte. Das hört sich erstmal nicht nach einem Quantensprung an. Allerdings muss man bedenken, dass ich „lediglich“ Java durch das doch sehr ähnliche Groovy ersetzt habe. Also hat eine Einzelmaßnahme 20% Code-Ersparnis gebracht. Setzt man das einfach mal naiv mit 20% Kostenersparnis gleich, ist man sehr schnell in Regionen, die interessant erscheinen (die meisten Offshoring-Untersuchungen sprechen von geringeren Einsparungspotenzialen).

    Außerdem ist zu bedenken, dass mein Terminplaner-Beispiel die Strukturen in den Vordergrund stellt und die Daten ignoriert (so hat der Benutzer nur seinen Namen und der Termin nur 4 Datenfelder). In einer vollständigen Terminplaner-Anwendung sind viel mehr Datenfelder zu verwalten (MS-Outlook hat für Kontakte so um die 30 Datenfelder). Und gerade wenn es nur um das Halten von Datenfeldern geht, spielt Groovy seinen LoC-Vorteil aus. Die 30 Datenfelder würden in Groovy ca. 10 LoC bedeuten und in Java ca. 130 LoC (beide Zahlen inkl. Leerzeilen).

    Nicht zuletzt habe ich die Terminplaner-Anwendung relativ stumpf auf Groovy umgestellt. Ich muss prüfen, ob sich der Code durch fortgeschrittene Groovy-Konzepte noch weiter vereinfachen lässt.

    Der Groovy-Code findet sich hier zum Download.

    Post bewerten

    Samstag, Mai 20, 2006

    TDD-2: Testabdeckung bei TDD-Code

    Ich habe mal die Testabdeckung bei meinem Terminplaner-Beispiel analysiert, das ich testgetrieben entwickelt habe. Dabei hat sich herausgestellt, dass die Testabdeckung nicht bei 100% lag, wie ich zunächst vermutet hätte, sondern bei gut 80%. Nach einigem Nachdenken und Rumprobieren habe ich entschieden, die Testabdeckung nicht auf 100% zu bringen (was problemlos möglich gewesen wäre).
    Die Reports der Testabdeckung sowie die Diskussion der Analyseergebnisse finden sich hier zum Download.

    Post bewerten

    Freitag, Mai 19, 2006

    Software-Architektur: Die vergessene Dimension?

    Wenn über Software-Architektur gesprochen wird, werden ihr die solche Funktionen zugeschrieben - sowohl bei klassischer Betrachtung wie auch aus dem Blickwinkel agiler Methoden:
    • Rahmen für die Realisierung der funktionalen Anforderungen setzen
    • Nicht-funktionale Anforderungen wie Wartbarkeit, Robustheit, Sicherheit etc. sichern

    Dabei wird aus meiner Sicht ein ganz wichtiger Faktor übersehen oder ignoriert. Die Software-Architektur beeinflusst ganz wesentlich die weitere Ausgestaltung des Entwicklungsprozesses und der Projektorganisation. Wie aufwändig die Koordination verschiedenen Entwicklungsteams in einem großen Projekt wird, ist ganz wesentlich von der gewählten Architektur bestimmt.

    Ich habe inzwischen eine ganze Reihe von Projekten erlebt, in denen die Architektur gewählt wurde, ohne auf den Entwicklungsprozess und die Projektorganisation zu achten. Die Konsequenz war immer eine sehr unangenehme Beschränkung der Möglichkeiten im Projektverlauf. In einem Fall hätte man ein schlecht laufendes Projekt retten können, wenn man die Entwicklermannschaft von 8 auf 20 Entwickler hätte erhöhen können. Die Architektur hat das aber verhindert. In einem anderen Fall hat die gewählte Architektur erzwungen, dass man ganz genau vorher planen musste, wer was tun muss. Als der Umstieg auf eine agilere, reaktivere Vorgehensweise mit kurzen Releasezyklen anstand, war das faktisch nicht möglich.

    Aus meiner Sicht muss bei der Definition und Weiterentwicklung der Architektur jeweils auch berücksichtigt werden, welche Beschränkungen und Möglichkeiten die Architektur für den Entwicklungsprozess und die Projektorganisation mit sich bringt. Und das bedeutet für viele Software-Architekten eine ganz neue zusätzliche Dimension in ihrer Tätigkeit.

    Post bewerten

    Dienstag, Mai 02, 2006

    TDD-1: Testgetriebene Entwicklung am Beispiel

    Ich habe zum Spaß mal zwei Sessions zu je 90 Minuten am Beispiel "Terminplaner" testgetrieben programmiert (Java und JUnit). Protokoll und Code gibt es hier zum Download. Vielleicht hilft es ja bereits in der jetzigen Form dem einen oder anderen beim Verständnis von TDD?

    Richtig interessant wird es aber erst später. Dann will ich verschiedene Aspekte des Beispiel-Codes und des Vorgehens beleuchten.

    Zwei interessante Beobachtungen kann man aber bereits jetzt machen:
    1. Ich war beim Programmieren wg. der fortgeschrittenen Zeit immer wieder mal abgelenkt. Das testgetriebene Vorgehen hat mich immer wieder schnell auf den richtigen Weg gebracht.
    2. Es gibt nur eine Testklasse für 5 Klassen. Man hätte auch Tests für die einzelnen Klassen schreiben können. Das schien mir aber immer doppelte Tests zu implizieren.

    Post bewerten

    Sonntag, März 26, 2006

    Revenge of the Nerds

    Durch Dierk König bin ich auf einen Artikel von Paul Graham aus dem Jahr 2002 gestoßen: Revenge of the Nerds. Dort argumentiert Paul Graham, dass die Programmiersprachen sich mit der Zeit immer weiter an LISP angenähert haben, allerdings immer noch nicht die Ausdruckskraft von LISP erreicht haben (das ist schon erstaunlich, wenn man bedenkt, dass LISP bereits 1958 erfunden wurde). Außerdem behauptet er, dass die Programmiersprache eine große Rolle bei der Produktivität spielt. Die zweite These erscheint mir sofort plausibel und passt auch mit den gängigen Untersuchungen zur Produktivität in Softwareprojekten zusammen.
    Die erste These war mir neu, scheint mir aber ebenso plausibel. Sie hat mich dazu animiert, nochmal an meine Studienzeit zurückzudenken, in der LISP-Programmierung zur Grundausbildung gehörte. Und tatsächlich: Die Programmiersprachen sind immer LISP-ähnlicher geworden und haben LISP immer noch nicht erreicht. Und ich trauere irgendwie doch immer mal wieder der Art und Weise nach, wie man LISP programmieren konnte. Es ist doch schon erstaunlich, dass man mit LISP bereits die Möglichkeit hatte, sich für sein Problem eine adäquate Sprache zu definieren und dann das Problem in dieser Sprache zu lösen. Modern ausgedrückt ist in LISP von Anfang an die Möglichkeit enthalten gewesen, DSLs (Domain Specific Languages) zu definieren. Smalltalk, Ruby, Python und Groovy sind trotz ihrer Dynamik nicht so ausdrucksstark geworden. Aber viel fehlt nicht mehr. Warten wir noch ein oder zwei Programmiersprachengenerationen ab und wir programmieren alle in LISP. Das heißt dann vielleicht etwas anders und hat vielleicht ein leicht andere Syntax, aber konzeptuell wird es LISP sein - wenn Paul Graham Recht hat. Irgendwie freue ich mich darauf und hoffe, dass ich selbst dann noch zum programmierenden Volk gehöre.

    Post bewerten

    Skype-Diskussion Java-Magazin: Technology First

    Im Java-Magazin 04/2006 wurde ein Artikel mit einer Skype-Diskussion veröffentlicht, an der ich auch beteiligt war. In der Diskussion ging es um die Frage, warum wir als Softwareentwickler die vielen tollen Techniken so selten einsetzen, obwohl wir sie lange kennen (Bsp.: Test-First, Entwurfsmuster etc.).
    Vor kurzem wurde ich von einem Leser des Artikels gefragt, ob die Diskussion tatsächlich so stattgefunden hat oder ob sie erfunden wurde. Die Diskussion hat tatsächlich stattgefunden und das Protokoll wurde lediglich etwas gekürzt und um Rechtschreib- und Grammatikfehler bereinigt.
    Der Artikel als PDF findet sich hier.

    Post bewerten

    Sonntag, März 05, 2006

    Ruby on Rails vs. ???

    Zur Zeit ist Ruby on Rails in aller Munde. Von vielen wird es für die Technologie der Zukunft gehalten. Aber gegen wen ist Ruby on Rails eigentlich positioniert?

    Ich bin kein Experte für Skriptsprachen a la PHP oder Perl, habe aber das Gefühl, dass Ruby on Rails gegenüber diesen Sprachen keinen wahnsinnig großen Fortschritt darstellt - klar ist die Sprache Ruby cooler, aber kann man dadurch seine Webanwendungen soviel schneller schreiben?

    Bliebe als Konkurrent also Java. Dort dürfte Ruby on Rails nur für einen kleinen Teil der existierenden Java-Kunden interessant sein. Wer sich strategisch für Websphere als Application-Server entscheidet, kann dann schlecht wichtige Anwendungen in Ruby in einer anderen Ablaufumgebung entwickeln. Bleiben also die Kunden übrig, die heute Java-Projekte starten und die sich keine strategischen Gedanken über Transaktionsmonitore oder Application-Server machen.

    Wenn sich allerdings Groovy und Grails als Java-Technologien verbreiten, ist das dann für die existierenden Java-Kunden nicht viel attraktiver als Ruby on Rails? Immerhin lassen sich ihre existierenden Projekte leicht mit Groovy integrieren.

    Ich finde Ruby als Sprache cool und Ruby on Rails für eine bestimmte Art von Anwendungen auch. Allerdings befürchte ich, dass der Coolness-Faktor nicht ausreicht, um eine nennenswerte Verbreitung zu finden. Die allermeisten Entwickler suchen sich ihre Programmiersprache schließlich nicht selbst aus. Und Manager sind bekanntermaßen relativ immun gegen Coolness...

    Post bewerten

    Donnerstag, Februar 16, 2006

    Hibernate-Buch erschienen

    Hibernate 3Ich habe soeben ein Belegexemplar des Buches "Hibernate - Persistenz in Java-Systemen mit Hibernate 3" vom dpunkt-Verlag erhalten, dass ich zusammen mit Robert Beeger, Arno Haase und Sebastian Sanitz geschrieben habe.

    Das Buch ist bei Amazon noch im Status "noch nicht erschienen", aber das wird sich in den nächsten Tagen ändern.

    Am 8. Mai 2006 halten wir auf der JAX in Wiesbaden einen ganztägigen Power-Workshop zu Hibernate 3.

    Post bewerten

    Samstag, Februar 04, 2006

    Defect Driven Design

    Darauf hat mich Jürgen Ahting in seinem Blog aufmerksam gemacht: Defect Driven Design.
    Demnach erklärt man einfach direkt nach Vertragsunterzeichnung, die Softare sei fertig für den Akzeptenztest. Der Kunde wird dann sagen, dass er das Icon auf dem Bildschirm nicht finden kann. Und damit hat man den ersten Fehler, der zu korrigieren ist. Also baut man ein Icon und erklärt erneut die Bereitstellung der Software. Der Kunde clickt auf das Icons und es passiert nichts. Und damit hat man den nächsten Fehler. Und so weiter und so fort.

    Das hört sich natürlich absurd an, aber ein paar sinnvolle Denkanstöße kann man da trotzdem draus gewinnen, glaube ich.

    Post bewerten

    Sonntag, Januar 29, 2006

    Agile Methoden unter Beschuss oder: Die Rache des Wasserfalls

    siehe http://www.waterfall2006.com

    Post bewerten

    Dienstag, Januar 24, 2006

    Blog zur Kundenrolle in Softwareprojekten

    Jürgen Ahting hat jetzt auch einen Blog. Hier geht es um die Kundenrolle in Softwareprojekten sowie die Wirtschaftlichkeit von Softwareprojekten.

    Post bewerten

    Sonntag, Januar 22, 2006

    Groovy kann Typen

    Ich hatte mir in einem früheren Blog-Eintrag für dynamische Sprachen wie Ruby gewünscht, dass man optional einen Typ nennen kann, der dann dynamisch zur Laufzeit geprüft wird. So kann man meiner Meinung nach die Lesbarkeit von Quellcode erhöhen. Nehmen wir als Beispiel folgende Methode (Syntax ist informell):

    def loescheKunden(kunde)

    Dann muss man die Doku oder die Methodenimplementation lesen, um herauszufinden, was hier übergeben werden muss. Das Kundenobjekt, die Kundennummer oder der Kundenname?

    Eine Deklaration mit Typ würde diese Frage sofort beantworten:

    def loescheKunden(Kunde kunde)

    Jetzt habe ich mich näher mit Groovy beschäftigt und festgestellt, dass das genau so in Groovy funktioniert. Man kann optional Typen angeben, die dann dynamisch geprüft werden. Wenn man keinen Typ angibt, verhält sich Groovy wie die anderen dynamischen Sprachen und prüft den Typ auch nicht.

    Post bewerten

    Donnerstag, Januar 12, 2006

    XP und Software-Engineering

    Vor ein paar Tagen hat mich Tammo Freese mit folgendem Argument infiziert:

    Wikipedia definiert: Die Softwaretechnik (software engineering) als Teilgebiet der Informatik beschäftigt sich mit der standardisierten ingenieursmäßigen Herstellung von Software und den damit verbundenen Prozessen.

    Die einzige Methode zur Softwareentwicklung, die sich wirklich Software Engineering auf die Fahnen schreiben darf, ist demnach eXtreme Programming. Schließlich definieren alle anderen Methoden nur grobe Blöcke für die weitere Arbeit. Wie diese Blöcke konkret mit Arbeit zu füllen sind, lassen sie offen. Nur eXtreme Programming definiert hinunter bis auf die Ebene von Minuten, wie vorzugehen ist: Test erweitern, bis er fehlschlägt. Code so ändern, dass der Test wieder durchläuft. Und dann geht es wieder von vorne los.

    Das ist ein weiteres Indiz dafür, dass die Industrialisierung der Softwareentwicklung erst jetzt mit den agilen Methoden stattfindet.

    Post bewerten

    Seminar: Kundenrolle in agilen Projekten

    Agile Projekte versprechen früh einsetzbare Software mit einem besonders günstigen Kosten-Nutzen-Verhältnis. Damit die Erfolge mit agilen Projekten auch realisiert werden können, muss der Kunde seiner geänderten Rolle auch gerecht werden. Am 20.02.2006 findet zum zweiten Mal das Seminar Aufgaben und Chancen des Kunden bei agiler Softwareentwicklung der Deutschen Informatik Akademie (DIA) in Köln statt.

    Ich führe das Seminar zusammen mit Jürgen Ahting durch.

    Auszug aus der Seminarankündigung: Agile Softwareentwicklung (z.B. mit dem Extreme Programming, XP) ist mehr als ein neues Schlagwort. In vielen Praxisprojekten wurde bereits die Leistungsfähigkeit agiler Ansätze nachgewiesen. Die konsequente Zusammenstellung erfolgreicher und bewährter Planungs-, Arbeits- und Programmiertechniken sowie die aufmerksame Beachtung und Nutzung ihrer gegenseitigen Einflüsse bietet neue Chancen zur erfolgreicheren und effektiveren Entwicklung von Software. Insbesondere ergeben sich zusätzliche Möglichkeiten, die Risiken und Kosten von Projekten zu steuern und zukünftige Kosten zu verringern.

    Agile Softwareentwicklung zielt darauf ab, mit vorgegebenen Ressourcen so schnell wie möglich den maximalen Nutzen für den Kunden zu realisieren, ohne dabei die Qualität zu kompromittieren. Ein wesentlicher Erfolgsfaktor für diese Nutzenoptimierung ist die enge und flexible Zusammenarbeit zwischen Kunden und Entwicklungsteam. Kurze Releasezyklen führen zu frühem Return-On-Investment und geben schnelles Feedback über Angemessenheit und Qualität der Software.

    Die Vorteile des agilen Vorgehens sind leichter zu verstehen als umzusetzen, weshalb auch agile Projekte scheitern können. Da der Kunde beim agilen Vorgehen eine zentrale Rolle einnimmt, kann er die Vorteile nur dann voll ausschöpfen, wenn er seine Rolle auch genau versteht und optimal ausfüllt. Deshalb ist es nicht nur für die Ausführenden sondern auch für die auf Kundenseite maßgeblich an agilen Softwareentwicklungsprojekten Beteiligten extrem wichtig, aus der praktischen Erfahrung in Projekten verschiedenster Größenordnungen zu lernen. So können sie die wirtschaftlichen Hintergründe der agilen Praktiken verstehen und ihre Rolle als Auftraggeber sinnvoll wahrnehmen und geschickt agieren. Nur dann wird es möglich sein, agile Entwicklungsprojekte optimal zu gestalten und zum Erfolg zu führen.

    Nähere Informationen zu dem Seminar gibt es auf der Website der DIA oder über den Flyer zum Seminar.
    Anmeldungen für das Seminar nimmt die DIA direkt entgegen.

    Post bewerten

    Sonntag, Januar 08, 2006

    Codelängen

    Bei meinen Recherchen zu Groovy bin ich über ein interessantes Beispiel gestoßen. Dasselbe kleine Programm einmal in C#, in Java und in Groovy sowie Ruby (Achtung: Der Ruby-Quellcode findet sich in den Kommentaren zu der Groovy-Seite. Man muss dort also nach unten scrollen. Leerzeilen habe ich nicht mitgezählt und ich habe bei Java und C# ein paar Zeilen abgezogen, die der Formatierung im Web geschuldet waren):

    • C#: 45 Zeilen Code

    • Java: 56 Zeilen Code

    • Groovy: 14 Zeilen Code

    • Ruby: 17 Zeilen Code



    Von der unterschiedlichen Zeilenanzahl zwischen Groovy und Ruby sollte man sich nicht verwirren lassen. Im Groovy-Beispiel wurde eine Methode einfach in eine Zeile geschrieben, für die im Ruby-Beispiel drei Zeilen verwendet wurden. Man kann sagen, dass die Implementation in Groovy und Ruby identisch ist - abgesehen von syntaktischen Kleinigkeiten.

    Bedeutet das jetzt einen relevanten Unterschied für die Praxis? Moderne IDEs helfen, auch den umfangreicheren Java- und C#-Code schnell zu erstellen. Der Autor der Java-Version hat mit IntellJ IDEA nur 10% des Codes wirklich eingetippt.

    Ich meine, da ist sehr wohl ein Unterschied. Schließlich wird Quellcode viel häufig gelesen als geschrieben. Für die Produktivität der Entwicklung ist daher ausschlaggebed, wie aufwändig das Lesen und Verstehen existierenden Codes ist und nicht wie schnell man den Code tippen kann. Und die einschlägigen Statistiken sagen, dass die Anzahl der Zeilen Code, pro Personentag entstehen ebenso konstant ist, wie die Anzahl der Fehler, die man durchschnittlich je 1.000 Codezeilen macht. Ob man also 1.000 Zeilen Code mit Java oder Groovy schreibt: Man braucht gleich lang und programmiert die gleiche Anzahl Fehler in den Code. Nur, dass man in 1.000 Zeilen Groovy viel mehr Funktionalität programmieren kann als in 1.000 Zeilen Java.

    Post bewerten

    Groovy

    Dynamische Programmiersprachen a la Python und Ruby haben in den letzten Jahren viel Aufmerksamkeit erhalten. Ein wenig untergegangen ist da bisher Groovy. Groovy ist Bestandteil der Java-Platform und mit dem JSR-241 spezifiziert.

    Groovy lehnt sich bei der Syntax an Java (Groovy-Syntax ist Java-Syntax mit weniger Regeln) an und ist von den Sprachkonstrukten ähnlich zu Python oder Ruby. Besonders interessant ist Groovy für Java-Programmierer, weil es insbesondere eine gute Integration mit Java gibt. Man kann Groovy-Code ganz einfach aus Java heraus aufrufen und umgekehrt auch Java-Code einfach aus Groovy. Damit hat man insbesondere gleich das ganze JDK in Groovy zur Verfügung.

    Dadurch kann man z.B. Swing-Code mit Groovy schreiben und die Kernfunktionalität der Anwendung mit Java. Vorteil: Der Groovy-Swing-Code ist kürzer und verständlicher als derselbe Code in Java.

    Und es gibt das Groovy-Äquivalent zu Ruby on Rails: Grails.

    Weitere - gut strukturierte - Informationen zu Groovy gibt es hier.

    Post bewerten

    Donnerstag, Januar 05, 2006

    Industrialisierung der Software

    Seit Jahrzehnten wird immer wieder gefordert, die Softwareentwicklung müsste endlich aus der Produktion lernen. Insbesondere die Planbarkeit der Softwareentwicklung wurde als Ziel formuliert. Automatisierte Code-Generierung mit CASE-Tools, Software-Fabriken, vollständige Spezifikationen etc. haben versucht, diesen Anspruch einzulösen - mit allenfalls bescheidenem Erfolg.
    Als Kontrapunkt dazu sind um die Jahrtausendwende (das hört sich doch mal monumental an :-) die agilen Methoden wie eXtreme Programming, SCRUM, Crystal etc. entstanden. Dabei hat sich immer deutlicher herausgestellt, dass sich in den agilen Methoden viele Ideen wiederfinden, die bereits das Produktiongewerbe revolutioniert hatten: Lean Production, Lean Manufacturing, Just In Time, Kaizen. Auf den Punkt gebracht haben das die Poppendiecks in ihrem empfehlenswerten Buch Lean Software Development.
    Also kann man sagen, dass mit den agilen Methoden die Industrialisierung doch noch Einzug in die Softwareentwicklung gehalten hat - nur eben auf eine ganz andere Art als ursprünglich gefordert.

    Post bewerten

    Mittwoch, Januar 04, 2006

    eXtreme Programming in der Financial Times Deutschland

    In der Financial Times Deutschland ist gerade ein Artikel über eXtreme Programming erschienen. Interessanterweise wird die Sinnharftigkeit nicht mehr in Frage gestellt. Jetzt machen es die Firmen nicht, weil die die Entwickler nicht wollen oder können. Und gleichzeitig sagen die Entwickler überall, sie können XP nicht einführen, weil ihr Management nicht mitspielt...

    Post bewerten

    Kritik zu unserem XP-Buch

    Hier gibt es eine Kritik zu Buch über eXtreme Programming, dass ich zusammen mit Henning Wolf und Martin Lippert geschrieben habe.

    Post bewerten

    Sonntag, Januar 01, 2006

    Hibernate 3-Buch: Beispielcode und XDoclet-Kapitel online

    Buch: Fit for Developing SoftwareIch habe an einem Buch über Hibernate 3 mitgeschrieben (zusammen mit Robert Beeger, Arno Haase und Sebastian Sanitz). Das Buch wird im Februar 2006 im dpunkt-Verlag erscheinen. Bereits jetzt gibt es Beispielcode aus dem Buch sowie ein Kapitel über XDoclet zur Generierung der Mapping-Dateien online zum Download.

    Post bewerten

    Freitag, Dezember 30, 2005

    Akzeptanztests mit FIT

    Buch: Fit for Developing SoftwareEs gibt seit kurzem ein Buch über Akzeptanztests mit dem Open-Source-Framework FIT. Das Buch deckt nicht nur FIT ab, sondern auch die Aufsätze Fitnesse und Fit-Library.
    Das Buch zeigt anschaulich, wie ausgehend von den umgangssprachlichen Anforderungen des Kunden einfach FIT-Tests entwickelt werden können, die sowohl für den Kunden/die Anwender wie auch die Softwareentwickler verständlich und aussagekräftig sind.
    Ich finde die Grundidee von FIT bestechend, Tests als HTML-Texte zu beschreiben. In HTML-Tabellen befinden sich die eigentlichen Tests, im Text drumherum erläuternde Beschreibungen. FIT stellt Hilfsklassen zur Verfügung, mit denen die HTML-Tabellen einfach ausgelesen und die Testergebnisse in die Tabellen zurückgeschrieben werden können.
    Neben der gemeinsamen Kommunikationsbasis zwischen Kunden und Entwicklern hat FIT auch einen ganz interessanten Effekt auf die Systemarchitektur. Wird FIT nach dem Test-First-Ansatz verwendet, führt es zu einem sprechenden Entwurf. Umgekehrt deckt FIT in einem Test-Last-Ansatz Schwachstellen im Entwurf auf: Immer wenn die programmierten Fixture-Klassen umständlich werden, liegt Refactoring-Bedarf vor.

    Post bewerten

    Samstag, Dezember 24, 2005

    Zweite Auflage erschienen: Wolf, Roock, Lippert: eXtreme Programming

    Buch: Wolf, Roock, Lippert: eXtreme ProgrammingInzwischen ist die zweite Auflage des Buches "eXtreme Programming" erschienen, dass ich zusammen mit Henning Wolf und Martin Lippert geschrieben habe.
    Insgesamt haben wir an dem Buch ziemlich viel verändert. Neben kurzen Skizzen anderer agiler Methoden (Scrum, Industrial XP, Feature-Driven-Development, Eclipse Entwicklungsprozess und V-Modell XT) haben wir den Bereich rund um die Vertragsgestaltung deutlich erweitert und auch dem oft vernachlässigten Thema der Explorationsphase ein eigenes Kapitel gewidmet.
    Direkt bei Amazon kaufen.

    Post bewerten

    Sonntag, November 20, 2005

    Geschwindigkeit vs. Beherrschbarkeit

    Die Standish-Group rechnet uns in ihrem CHAOS-Report regelmäßig vor, wie schlecht es um die Softwareentwicklung als Industriezweig steht: Termine werden nur selten eingehalten, Budgets maßlos überschritten und die gelieferte Funktionalität ist unpassend.
    Allen ist seit Jahrzehnten klar: "Wir müssen was tun". Ebenfalls schon lange ist klar: "Wir müssen schneller werden!" So rufen es Entwickler und IT-Manager ins Marktgetümmel und die kommerziellen und nicht-kommerziellen Hersteller antworten: "MDA, MDSD, Spring, Hibernate, JSF, SOA, etc.". Die einschlägigen IT-Konferenzen sind voll mit diesen Themen. Diese Technologien werden uns retten. Oder doch nicht? Was haben uns denn die Technologien gebracht, die vor wenigen Jahren als Heilsbringer verkauft wurden (CASE, Software-Factories, Java, etc.)? Ich will nicht behaupten, dass diese Technologien oder ihre aktuellen Hype-Nachfolger keine positiven Effekte hatten. Bezogen auf die Kriterien der Standish-Group lässt sich aber kein nennenswerter Fortschritt ausmachen.
    Wenn man genauer hinsieht, bemängelt der CHAOS-Report auch gar nicht, dass wir zu langsam arbeiten. Kritisiert wird, dass wir unsere Projekte nicht beherrschen. Softwareprojekte wissen häufig bereits kurze Zeit nach dem Kick-Off nicht mehr, wo sie stehen. Davon, eine vernünftige Prognose für die Zukunft zu haben, können diese Projekte nur träumen.
    Naja, aber immerhin dürften die neuen Technologien auch nicht schaden. Nein? Doch! Die Einführung einer neuen Technologie oder Vorgehensweise bringt immer Instabilität. Eine neue Technologie in ein instabiles Projekt einzuführen, macht das Projekt also nicht stabiler, sondern instabiler.
    Folglich sollten neue Technologien immer nur auf der Basis eines stabilen Projektes eingeführt werden. Die Einführung muss dann aktiv begleitet werden, um nach der unausweichlichen Instabilität schnell wieder in stabiles Fahrwasser zu kommen.
    Langer Rede kurzer Sinn: Beherrschbarkeit kommt vor Geschwindigkeit.

    Post bewerten

    Hibernate 3 auf der W-JAX

    Ich habe auf der W-JAX am 14.11.05 zusammen mit Arno Haase und Robert Beeger einen Power-Workshop zu Hibernate 3 gegeben. Ca. 70 Teilnehmer ließen sich für Hibernate-Grundkonzepte erläutern und vollzogen die Beispielprogramme an ihren Notebooks nach.
    Interessanterweise hatte ca. ein Drittel der Teilnehmer bereits Projekterfahrungen mit Hibernate. Ich war etwas überrascht über diesen hohen Anteil, weil die Ankündigung des Power-Workshops explizit Hibernate-Einsteiger als Zielgruppe definierte.
    Gerade diese Mischung hat dann aber doch einige interessante Impulse gegeben. Die Teilnehmer mit Hibernate-Erfahrung konnten interessante eigene Erfahrungswerte beisteuern.
    Die beim Workshop behandelten Themen umfassten:

    • OR-Mapping mit XML-Mapping-Dateien
    • Queries mit HQL und Criteria-API
    • Lifecycle persistenter Objekte
    • Sessions, Transaktionen und Caching
    • Best Practices für Web-Anwendungen mit Hibernate
    • Best Practices für Client-Server-Anwendungen mit Hibernate
    • Zusammengesetzte Primärschlüssel

    Die Folien zum Power-Workshop sowie den Beispielcode kann man bei it-agile herunterladen.

    Post bewerten

    Samstag, November 12, 2005

    Neues Buch über testgetriebene Entwicklung

    Buch: Testgetriebene Entwicklung mit JUnit und FITJetzt ist es endlich da, das Buch über testgetriebene Entwicklung von Frank Westphal. Da fragt man sich doch gleich, ob die Welt noch ein Buch übers Testen braucht. Auch über JUnit und testgetriebene Entwicklung existieren bereits sehr gute Bücher (z.B. von Johannes Link oder Kent Beck). Den Unterschied finden wir im Untertitel zu Franks Buch: "Wie Software änderbar bleibt". Bei Frank geht es nicht primär darum, wie JUnit funktioniert und wie man die ganzen Probleme löst, die einem beim Testen mit JUnit so widerfahren (Datenbanken, Threads, Application-Server). Vielmehr geht es darum, wie man Software in der heutigen schnell-lebigen Zeit mit seinen agilen Vorgehensweisen entwickeln kann, ohne dass sie einem schon nach wenigen Monaten zusammenbricht. Testgetriebene Entwicklung ist lediglich das Hilfsmittel, dass Frank - mit Recht - dazu verwendet. Und so wundert es nicht, dass auch diskutiert wird, wie sich Refactoring und kontinuierliche Integration im Zusammenspiel mit testgetriebener Entwicklung entfalten und wie man mit Mock-Objekten die Komponenten seines Softwaresystems entkoppelt.
    Der Abschnitt über Akzeptanztests am Buchende schlägt ebenfalls genau in diese Kerbe.
    Insgesamt hat Frank ein Buch vorgelegt, dass nicht nur sehr verständlich geschrieben ist, sondern dass auch einen wichtigen eigenen Beitrag liefert.

    Post bewerten

    Freitag, Oktober 28, 2005

    Erst Schreiben, dann tun...

    In einem größeren Projekt arbeite ich als Ürojektleiter für drei Teilprojekte. Da komme ich nicht mehr selbst zum Programmieren. Vielmehr gehören Abstimmungen mit diversen Kunden, Tracking, Teambildung, Abrechnungsgefummel etc. zu meinen Aufgaben. Um herausfinden, ob ich was von meinen Tätigkeiten sinnvoll delegieren kann, habe ich jetzt eine Weile lang ein Log-Buch geführt. In dem Log-Buch habe ich jeweils mit Uhrzeit kurz aufgeschrieben, was ich gemacht habe. Die Log-Buch-Einträge sind zwischen 3 Minuten ("Smalltalk mit Entwickler XYZ") und 3 Stunden ("Releaseplanungsmeeting für ABC") lang.
    Dabei habe ich ein paar interessante Dinge gelernt:

    1. Ich mache viel zu selten Pause.
    2. Das Führen des Log-Buchs ist fast kein Overhead (das hatte ich zunächst befürchtet).
    3. Ich habe irgendwann angefangen, erst aufzuschreiben, was ich als nächstes tun werde und dann habe ich es getan. Das diszipliniert ungemein. Kein rumgetrödel mehr, kein E-Mail-Checken alle 15 Minuten, kein planloses Browsen im Internet. Das hat zu einer deutlichen Effizienzsteigerung bei meiner eigenen Arbeit geführt. Allerdings ist das auch anstrengender. Mehrere 10-Stunden-Tage am Stück kann ich so nicht durchhalten. Brauche ich jetzt aber auch nicht mehr. Mal sehen, wie sich diese Technik für mich in der Zukunft weiter bewährt.

    Post bewerten

    Montag, Oktober 24, 2005

    Verantwortung in der Softwareentwicklung

    Das kennt man als Softwareentwickler: Der Chef oder Projektleiter kommt ins Büro und braucht unbedingt ganz schnell noch Feature XYZ für das anstehende Release. Also bauen die Entwickler das geforderte Feature mehr schlecht als recht ein. Es tut ungefähr das, was gefordert ist. Die interne Struktur ist aber äußerst bescheiden. Theoretisch kann man die interne Qualität später bereinigen. Es weiß aber jeder, dass man die Zeit dafür nicht bekommt. Also bleibt alles, wie es ist und das System degeneriert Stück für Stück. Für die meisten Entwickler ist das der unvermeidliche Gang der Dinge.
    Die Entwickler sind also die Opfer ihrer chaotischen Chefs. Möglich. Allerdings ist diese Sichtweise weder nützlich noch ermutigend. Ich jedenfalls sehe mich ungern als Opfer. Und die Psychologen lehren uns, dass wir andere Menschen nicht ändern können. Wir können nur unser eigenes Verhalten ändern. Also brauchen wir gar nicht erst darauf zu hoffen, dass unsere Chefs zur Vernunft kommen. Was also können wir als Entwickler tun, um unsere Situation zu verbessern?
    Ich schlage vor, dass Entwickler Verantwortung für ihre Arbeit übernehmen. Kein Entwickler darf Code programmieren, der seinen eigenen Qualitätsansprüchen nicht genügt. Auch dann nicht, wenn ein Chef oder Projektleiter Druck ausübt. Häufig bekommen die Chefs/Projektleiter dadurch genau das Feedback, dass ihnen bisher gefehlt hat. Sie konnten ja gar nicht einschätzen, wie stark sich ihre Sonderwünsche auf die interne Qualität des Systems ausgewirkt haben.
    Und was ist, wenn der Chef/Projektleiter unbedingt auf der Quick-Hack-Umsetzung seiner Features besteht? Dann bedeutet das einfach nur, dass Entwickler und Chef/Projektleiter nicht zusammenarbeiten können.

    Post bewerten

    Freitag, September 16, 2005

    Ruby vs. Java

    Ruby on Rails is a web programming framework written in a dynamic oo programming language called Ruby. Ruby exists for quite some time but with Ruby on Rails it was hyped during the last months.
    There are some key features that make Ruby attractive:

    • No compile time since it is interpreted.
    • Compact syntax.
    • Powerful reflection.

    I was always a fan of statically typed languages like Java. With this background there are drawbacks to the Ruby approach:

    • You can't use a compiler to find type errors.
    • By reading source code it is hard to find out what type an object might have.
    • There are nearly no refactoring tools for Ruby available.
    • Ruby has a de facto standard for web applications (Ruby on Rails) but only poor non-standard support for rich client destop applications.

    But also Java has its drawbacks. After having several years of experience with large J2EE projects I these drawbacks became clearer to me.

    • Although some Java IDEs can compile incrementally, recompilation of large parts of the project is often neccessary and slow.
    • Java programs are full of type casts breaking type safety. That mighth change with the generics of Java 5.
    • With J2EE you need lots of hard to understand XML configuration.
    • The XML configuration files break type safety. The compiler becomes less and less useful.
    • The refactoring support for XML configuration files is quite poor in the moment.
    • Java needs much more code and configuation than Ruby. Here is a comparison. In that comparison the Ruby application also is faster than the Java application.

    To me the obvious difference between Ruby and Java always was type checking. Ruby does no automatic type checking. Java does automatic type checking during compile time. Therefore Java can find more bugs than Ruby. Now I no longer believe that type checking is the point. As I wrote above type checking becomes less useful in Java systems. In Ruby and in Java a lot of real value type checking is done in unit tests. Perhaps the type checking in Ruby systems is even stronger than in Java systems. In a Ruby system the programmer knows that he has to write unit tests. In Java it seems optional to a lot of developers to write unit tests - do they think that the compile time checkings are sufficient?

    So, what are the key differences between Ruby and Java in real world projects? I think there a three main aspects:

    • Ruby programs are more compact than Java programs. Less lines of code means less programming errors. That is a clear advantage for Ruby.
    • Refactoring is now state of the art. Java IDEs have powerful refactoring tools. Ruby has poor refactoring support und in some aspects the Ruby refactoring support will stay weak. It has the Smalltalk problem that you never now on what object a method will be called. Therefore renaming a method has to rename all methods with the same name. Therefore a big plus for Java now. But hopefully Ruby refactoring tools will evolve.
    • Source code is written once and read many times. Therefore source code has to be easy to understand. I find it helpful to know what type of object the programmer of a method expects as a parameter. In Java it is easy. The type is declared in the method signature. In Ruby programs it is often hard to find out what the programmer really expected. Conventions help but I have the feeling that the Java way is superior here.

    So, what has Ruby to do to gain world domination? Here are my 2 cents:

    • Ruby needs a refactoring tool. At least with "Rename Class", "Rename Method", "Rename Attribute", "Extract Method" and "Inline Method". The last one might sound a bit special but Tammo Freese described the real power of the "Inline Method" refactoring in a presentation at the XP 2003 conference. We used his ideas in our Refactoring Book.
    • Ruby needs at least a convention used by everyone to annotate the expected type of an object. It would be even better to check the type at runtime. Perhaps there should be a language extension for annotating dynamic type checks in an elegant standard way. This information could be used by refactoring tools also to be more specific when refactoring methods.

    Post bewerten

    Freitag, Juli 08, 2005

    JUnit 4.0 ante portas

    Frank Westphal wrote a good overview about the new features of JUnit 4.0 (in german language only): http://www.frankwestphal.de/JUnit4.0.html

    Post bewerten

    Samstag, Juni 18, 2005

    Refactorings in großen Projekten

    Martin Lippert and I have written a book about doing Refactorings in large projects. The book is available in german from dpunkt.

    The Javamagazin has reviewed the book in July 2005: "Fazit: Das Buch ist auch ohne große Vorkenntnisse als Einstieg in das Thema Refactoring und Smells hervorragend geeignet."

    Post bewerten

    UML-Shapes für Visio

    One of the tools I like most is Visio. Visio comes with a set of UML shapes. Unfortunately these shapes try to be intelligent creating a lot of hurdels. Therefore I prefer less intelligent flexible to use shapes like these: http://www.phruby.com/stencildownload.html

    Post bewerten

    Donnerstag, April 28, 2005

    Tonabnehmer-Podcast by Frank Westphal: Agile Software Development

    Frank Westphal puts interviews with people doing agile projects on his web: Tonabnehmer. Very interesting. Put the mp3 on your MP3 player and consume it in the subway. The interviews are done in german language.

    Post bewerten

    Donnerstag, April 07, 2005

    eXPlain Project Management Tool

    eXPlain is a story card management system for agile projects, namely eXtreme Programming. In contrast with XPlanner eXPlain supports effort estimations in effort points (not person hours). Moreover eXPlain has a much smaller than XPlanner. All the XPlanner features I never used, aren't there in eXPlain.
    And eXPlain is written in Ruby and is therfore ridiculous small in code size. Ruby seems to be the upcoming star for web applications.

    Post bewerten

    Mittwoch, März 09, 2005

    Weblog for IT-Managers

    it-agile has started a (german) weblog addressed at IT-Managers (project manager, head of it department etc.): http://managerblog.it-agile.de

    Post bewerten

    Luntbuild

    Luntbuild is a new build process management tool (like Cruise-Control). It has a nice and easy to use web interface (you don't have to edit any files). We started to use it in one project and got promising results.
    The most important drawback in contrast with Cruise-Control is the missing Quiet-Time-Period for CVS. In projects with many concurrent check-ins that use CVS the missing feature may cause some trouble.

    P.S.: It seems that the current Luntbuild download has a little bug (since it requires Starbase classes). The bug database of Luntbuild has hints on how to fix the problem without programming.

    Post bewerten

    Cobertura

    Cobertura is a fork of the GNU version of JCoverage. In contrast with GNU JCoverage there is some development activity at Cobertura. Some long known bugs in JCoverage are fixed in Cobertura now (e.g. the problems occurring when more than some 100 files had to be instrumented).
    There where also problems when we tried to use XRadar with GNU JCoverage which are fixed in Cobertura now.
    In one project we switched from JCoverage to Coberatura and it worked fine.

    Post bewerten

    Freitag, März 04, 2005

    Evil Singletons

    I have built quite a lot systems as a developer and I have seen much more systems as a consultant. Now I'm strongly convinced that Singletons are evil. Uncle Bob has written a nice article on Singletons.

    Post bewerten

    Mittwoch, Januar 19, 2005

    Weblog for Developers at it-agile

    it-agile has started a weblog targeted at developers: http://entwicklerblog.it-agile.de (german only).

    Post bewerten

    Mittwoch, Januar 05, 2005

    New Job

    I changed jobs at 01-jan-2005. Now I work as an IT consultant for it-agile. it-agile offers agile software development and consulting / training for agile methods like eXtreme Programming. My new EMail address at it-agile is "stefan DOT roock AT it-agile DOT de".

    Post bewerten

    Dienstag, Dezember 28, 2004

    Slides of Talk: Refactorings in Large Projects

    Here are the slides of my talk "Refactorings in großen Softwareprojekten" ("Refactorings in Large Software Projects") which I gave at the XP Days in Karlsruhe. Since the talk was given in german the slides are german also.

    Post bewerten

    Sonntag, Dezember 26, 2004

    Managing Module Dependencies in Large Systems

    In larger projects it is nearly impossible to avoid degeneration of large scale structures without tool support. It is far too easy to import missing packages with one key-stroke in modern IDEs like Eclipse or IDEA.
    My experience is that almost every projectwith more than 500 classes has unwanted dependencies between its modules (module = coherent set of packages). Often even cycles between modules occur.
    There are some Open-Source solutions that help to avoid unwanted dependencies in Java projects or at least discover them early:
    • Put every module in its own JAR file. An ANT build script can then discover unwanted depdencies during compilation and generation of the JAR files.
    • If Eclipse is used: Define an Eclipse project for every module and let Eclipse manage the dependencies.
    • The use of the Eclipse plugin model allows even finer control but brings some overhead with it.
    • Define the allowed dependencies in a Fitnesse test. There is an easy to use solution named JDependFixture. Especially when you use Fitnesse already the your project JDependFixture may be a convenient solution.
    • XRadar is also based on JDepend and checks dependencies between modules (in XRadar modules are called subsystems). XRadar uses a XML definition of modules and dependencies and creates a graphical representation of the existing dependencies. XRadar is especially convenient when a nightly build process is in place, for example based on Cruise-Control.

    Post bewerten

    Mittwoch, Dezember 08, 2004

    Book: Refactorings in Large Projects

    Martin Lippert and I wrote a book about Refactorings in Large Projects that is out now for review. We are very interested in your feedback. Simply write an email to stefanATstefanroockDOTde.

    Post bewerten

    Taxonomy of code smells

    There is a new taxonomy of code smells.

    Post bewerten

    Sonntag, November 21, 2004

    Large Refactorings at XP-Days Karlsruhe

    I will talk about Large Refactorings at the XP-Days 2004 in Karlsruhe.

    Post bewerten

    Sonntag, November 14, 2004

    Distributed Computation@home

    SETI @ home was the first software for distributed computing at home: CPU time not used by the user is used for a really large distributed computation project. The experiences with SETI @ home were used to create a content independent platform for distributed computing: BOINC.
    There are additional public projects for distributed computation using BOINC available at the BOINC link given above.

    Post bewerten

    Freitag, November 05, 2004

    Rich Client Patterns

    Martin Fowlers book "Pattern of Enterprise Application Architecture" lacks patterns for rich client applications. On his website Martin Fowler has collected first patterns for rich client applications.

    Post bewerten

    Samstag, Oktober 30, 2004

    Multiple Customers in XP

    Ron Jeffries has written a short but interesting article about how to deal with multiple customers: Petition the King. He uses the metapher of villagers coming to the king regularly (one a month or one every two weeks) to explain their requests. The king has limited resources and decides about the usage of the resources.
    In XP the king is not a developer since decisions about distributing resources is a bussiness decision not a technical desicion. Therefore king is a kind of super customer, head of marketing for a product company or something similar.

    Post bewerten

    Freitag, Oktober 22, 2004

    Design in Agile Methods

    One of the most controverse aspects of agile methods is the role of design. In eXtreme Programming the practice is stated explicitly: Simple Design.
    Buzz words describing simple design are:
    • You ain't gonna need it (the YAGNI principle).
    • Keep it simple, stupid (the KISS principle).
    • Design for Today.
    • No Big Design Upfront (BDUF).

    Two articles (available online) about the topic give further insights:

    Post bewerten

    Sonntag, September 19, 2004

    Paper on Pair-Programming

    There is a new paper on Pair-Programming online - only in german.

    Post bewerten

    Donnerstag, September 16, 2004

    Managing ANT scripts

    In larger Java projects the ANT scripts tend to become complicated and hard to handle. Too often the ANT scripts produce incomplete results or need too much runtime. Eric M. Burke wrote down useful best practices for ANT scripts.
    And he wrote a little tool that visualizes the dependencies of ANT targets: AntGraph.

    Post bewerten

    Dienstag, August 31, 2004

    How to write unmaintainable code

    Funny and true article: http://mindprod.com/unmain.html

    Post bewerten

    Visibility of Automatic Build

    There is a cool kit for making the results of automatic builds (e.g. with Cruise-Control) visible: Bubble, Bubble, Build's In Trouble. And it costs less than 100 USD.

    Post bewerten

    Donnerstag, August 26, 2004

    XRadar: Structural Analysis for Java projects

    We startet to use XRadar in a larger project for structural analysis, e.g. dependency checks between subsystems and packages.

    XRadar is open source and combines a lot of useful small tools like JDepend and PMD to form a complete analysis suite. We integrated XRadar into our Cruise-Control build process and got helpful results about the structure of our system.

    Post bewerten

    Dienstag, August 17, 2004

    Time Travel Pattern Language

    I just discovered a paper describing the Time Travel pattern language for objects that change. The patterns address objects that have a browsable history of modifications where the modifications can have effects in the past and the future. These problems often arise with contracts where the time of making the modification can differ from the time where the modification takes effect.
    Example: One week ago I buyed a new car. Now I send a notice to my insurance company. While the contract is modified tomorrow when my notice reaches the insurance company, the modification has to take effect one week ago in the past.
    Once I was in a project at an insurance company and we had exactly the same problems. At the end we came to very similar solutions. Had we known the Time Travel pattern language we could have saved a lot of time, not only to find the solutions but more important to communicate the problems and the solutions.

    Post bewerten

    Montag, August 16, 2004

    Unit Test Smells

    The term smell was taken from the refactoring discussion. There a code smell comes from an ugly piece of source code that should be restructured (refactored) as soon as possible. Typical code smells are duplication of code, unneccessary indirections etc.
    The term smell can be transferred to a lot of other “domains”, e.g. to the wide area of testing. This article is a first attempt to collect smells for the area of unit tests.

    Post bewerten

    Freitag, August 06, 2004

    C-JDBC: open-source inexpensive DB clustering

    When searching for techniques to create Java enterprise applications without buying and using heavyweight products one should take a look at C-JDBC. C-JDBC is an open-source product that supports the RAIDb concept (Redundant Array of Inexpensive Databases): C-JDBC encapsulates several database instances behind a regular JDBC api. To introduce C-JDBC into a project existing code needn't be modified as long as all database access is handled via JDBC.

    Post bewerten

    Donnerstag, August 05, 2004

    Modular Software with PicoContainer

    Most OO systems claim to be modular but very few really are. Normally OO systems have cycles between they modules. Even if there are no cycles the dependencies between the so called modules are chaotic and inflexible. A typical result is that developers can't instantiate a small set of classes for unit testing without having the rest of the system.
    PicoContainer is an open-source project that provides a IoC-Container (IoC = Inversion of Control) that is very useful for defining and managing the dependencies between modules.

    I collegue asked me once when I would PicoContainer into a project:
    • Right from the beginning?
    • Even for prototyping?
    • When the system exceeds a certain size?
    I think that projects should use PicoContainer right from the beginning and even for prototypes. Even for very small prototypes PicoContainer pays off measured in Lines of Code and it adds very small overhead to the project.
    Adding PicoContainer later to a project results in refactoring and will therefore often not done.

    Post bewerten

    Sonntag, August 01, 2004

    Do You like to Eat an Elephant?

    There is an funny and interesting article about EJB out there, called "Don't Make me Eat the Elephant Again". The autor argues that for most project EJB ist just too big and suggests some lightweight approaches to building Java Enterprise Applications.
    I like the article very much since I know the suffer the author describes from my programming and consulting experience. It is the time for a change!

    There is a very interesting book about the topic: Bruce Tate, Justin Gehtland: "Better, Faster, Lighter Java".

    Post bewerten

    Samstag, Juli 31, 2004

    SCRUM Master

    I participated the SCRUM Master training in Karlsruhe held by Joseph Pelrine. That was fun and now I'm a certified SCRUM Master.
    BTW: A collegue of mine said that "SCRUM Master" sounds like something evil. I try to be not too evil :-)

    Post bewerten

    Funny GridBagLayout

    Its always a highlight when profession meets fun. A very funny and striking description of Java's GridBagLayout is available as an interactive weblog.

    Post bewerten

    Donnerstag, Juli 15, 2004

    JMigrator 0.4.0 released

    I released the first version of JMigrator at Source-Forge as an Eclipse 3 plugin.
    If anybody is interested in participating at the further development, please contact me.

    Post bewerten

    Montag, Juli 05, 2004

    Trashcan Frameworks

    Application specific frameworks often degenerate and become Trascan Frameworks. I have written my thoughts in a short article "Trashcan Frameworks".

    Post bewerten

    Sonntag, Juli 04, 2004

    Large Refactorings and Fitnesse at Java Forum Stuttgart

    Martin Lippert and I held a lalk about Refactorings in large Projects at the Java Forum Stuttgart. The slides are here (german). I submitted a presentation about aceptance testing with Fitnesse. This was accepted as a failover presentation. Since no other presentation was cancelled, the presentation wasn't held. But the slides are here for download although (german).

    Post bewerten

    Freitag, Juni 25, 2004

    Refactoring Example for Beginners

    I found a small code example that could be used by refactoring beginners.
    • What smells are in the code?
    • What refactorings can be used to remove the smells?
    • How small can the new solution be? (If you send me your refactored solution I may publish it here.)

    P.S.: The code in C# but it should be easy to convert it to Java.
    P.P.S.: If someone has the code in Java, please send me a link.

    Post bewerten

    Samstag, Juni 19, 2004

    Customer related blog of Chris Matts

    Chris Matts was a panelist at XP2004 conference. He works as a consultant for customers using Agile Methods. He has some very interesting things to say - a lot of these can be found at his blog.

    Post bewerten

    Book: Agile Software Development in the Large

    First hand experiences from and guidances for doing large agile projects are very rare. Jutta provides helpful insights into large projects in general and the special challenges of doing large projects with agile methods like eXtreme Programming, Scrum or Crystal.

    Jutta Ecksteins book "Agile Software Development in the Large: Diving into the Deep" (Dorset House Publishing) is published now. A german translation was published under the title "Agile Softwareentwicklung im Großen" (dpunkt Verlag).



    Post bewerten

    Donnerstag, Juni 17, 2004

    Master Thesis with Empirical Data about Agile Methods

    The master thesis of Carsten Dogs and Timo Klimmer provides some interesting empirical data about agile methods like eXtreme Programming.

    Post bewerten

    Samstag, Juni 12, 2004

    Refactorings in großen Softwareprojekten

    Martin Lippert and I have written a book about doing Refactorings in large projects. The book is available in german now from dpunkt. The english translation should be available in a few months.

    Post bewerten

    XP 2004: Agile Project Controlling

    Henning Wolf and I have given a talk about Agile Project Controlling at the XP 2004 conference.

    Post bewerten