(23.05.05 21:05)

In seinem kürzlich veröffentlichten Beitrag Flexible JUnit assertions with assertThat() beschreibt Joe Walnes eine elegante Möglichkeit, die Leserlichkeit von JUnit Tests merklich zu erhöhen.

Wie Joe treffend bemerkt, ist man beim Schreiben von JUnit Testfällen immer wieder gezwungen, sich aus der Vielzahl der verfügbaren assert-Varianten die richtige auszusuchen: assertEquals, assertNotEquals, assertStringContains, assertInRange, assertIn, etc.

Mit Hilfe der Constraint-Library von jMock geht das Schreiben aussagekräfitger Assertions wesentlich eleganter. Mit Hilfe von jMock Constraints können präzise Erwartungen für Mock-Objekte festgehalten werden. Aber die Constraints lassen sich ganz einfach auch für eigene Zwecke verwenden. Zum Beispiel, um eine eigene JUnit assert -Methode zu schreiben, die ein Object und ein Constraint als Argument nimmt, und die als Ersatz für die üblichen JUnit assert-Methoden dient:

protected void assertThat(Object something,
                          Constraint matches) {
  if (!matches.eval(something)) {
    StringBuffer message = 
      new StringBuffer("\nExpected: ");
    matches.describeTo(message);
    message
      .append("\nbut got : ")
      .append(something).append('\n');
    fail(message.toString());
  }   
}

Mit Hilfe dieser Methode können wir nun Zusicherungen schreiben, die sich wesentlich besser lesen lassen:

assertThat(something, eq("Hallo"));
assertThat(something, eq(true));
assertThat(something, isA(Component.class));
assertThat(something, contains("Weltwunder"));
assertThat(something, same(Model.ID));
assertThat(something, NULL);
assertThat(something, NOT_NULL); 

Das alleine scheint mir schon ziemlich gut. Aber es wird noch besser: Normale JUnit Assertions sind in der Regel nicht selbsterklärend und damit wenig hilfreich, wenn es darum geht, rasch erkennen zu können, was schief gegangen ist. Ganz anders sieht die Sache mit der obigen AssertThat Variante aus. Denn jMock Constraint Fehlermeldungen sind selbsterklärend.

Joe macht dazu ein gutes Beispiel:

assertThat(something, or(contains("color"), 
                         contains("colour")));

Diese Assertion liefert eine aussagekräftige Fehlermeldung:

junit.framework.AssertionFailedError:
Expected: 
  (a string containing "color" or a string 
   containing "colour")
but got : hello world

Bei Verwendung der herkömmlichen JUnit Assertions bekämen wir dagegen nur ein lahmes junit.framework.AssertionFailedError zu sehen. Das obige Beispiel zeigt übrigens auch sehr schön, wie sich Constraints einfach verknüpfen lassen. Für weitere Details verweise an dieser Stelle auf Joes Beitrag.

Ich habe zu Testzwecken Tests in einem aktuellen Projekt auf assertThat umgestellt und muss sagen, dass ich mit den Ergebnissen bis jetzt sehr zufrieden bin; endlich liefern unsere Tests aussagekräfitge Fehlermeldungen, ohne dass wir mühsam eigene Assert-Meldungen schreiben müssen.

Fazit: Ein Grund mehr, sich jMock zu besorgen, auch wenn man sonst kein Fan von Mocks ist.

-nemo :-)

Über diesen Artikel diskutieren.

Zugriffe heute: 1 - gesamt: 4798.




Domänengetrieben = ... Suchen mit Clusty

Druckbare Version