Was ist die tatsächliche Verwendung von 'fail' im JUnit-Testfall?

122

Was ist die tatsächliche Verwendung von 'fail' im JUnit-Testfall?

Sanju
quelle

Antworten:

137

Einige Fälle, in denen ich es nützlich gefunden habe:

  • Markieren Sie einen Test, der unvollständig ist, sodass er fehlschlägt und Sie warnt, bis Sie ihn beenden können
  • Stellen Sie sicher, dass eine Ausnahme ausgelöst wird:
try{
  // do stuff...
  fail("Exception not thrown");
}catch(Exception e){
  assertTrue(e.hasSomeFlag());
}

Hinweis:

Seit JUnit4 gibt es eine elegantere Möglichkeit, um zu testen, ob eine Ausnahme ausgelöst wird: Verwenden Sie die Anmerkung @Test(expected=IndexOutOfBoundsException.class)

Dies funktioniert jedoch nicht, wenn Sie auch die Ausnahme überprüfen möchten, die Sie dann noch benötigen fail().

sleske
quelle
5
Betrachten Sie diesen Blog-Beitrag über die relativen Vorzüge von Fail gegen erwartete Annotation: blog.jooq.org/2016/01/20/…
lbalazscs
4
@sleske "Wenn Sie auch die Ausnahme überprüfen möchten, müssen Sie immer noch fail ()" - nein. ExpectedException ist der Weg, siehe github.com/junit-team/junit4/wiki/exception-testing
Kraxor
@kraxor: Stimmt, wusste nichts davon, als ich die Antwort schrieb (es war wahrscheinlich noch nicht einmal da).
Sleske
14

Angenommen, Sie schreiben einen Testfall für einen -ve-Flow, bei dem der zu testende Code eine Ausnahme auslösen soll

try{
   bizMethod(badData);
   fail(); // FAIL when no exception is thrown
} catch (BizException e) {
   assert(e.errorCode == THE_ERROR_CODE_U_R_LOOKING_FOR)
}
Kartheek
quelle
10

Ich denke, der übliche Anwendungsfall besteht darin, es aufzurufen, wenn in einem negativen Test keine Ausnahme ausgelöst wurde.

So etwas wie der folgende Pseudocode:

test_addNilThrowsNullPointerException()
{
    try {
        foo.add(NIL);                      // we expect a NullPointerException here
        fail("No NullPointerException");   // cause the test to fail if we reach this            
     } catch (NullNullPointerException e) {
        // OK got the expected exception
    }
}
Philant
quelle
3
Wenn Sie im catch-Block nichts überprüfen, können Sie mithilfe der Annotation der Methode @ExpectedException (NullNullPointerException.class) deklarieren, dass Sie eine Ausnahme (einer besonderen Art) erwarten.
FrVaBe
8

Ich habe es für den Fall verwendet, dass bei meiner @ Before-Methode etwas schief gelaufen ist.

public Object obj;

@Before
public void setUp() {
    // Do some set up
    obj = new Object();
}

@Test
public void testObjectManipulation() {
    if(obj == null) {
        fail("obj should not be null");
     }

    // Do some other valuable testing
}
Ryan D.
quelle
1
Ja, Testvoraussetzungen sind gut. Wenn Sie jedoch sicherstellen möchten, dass die @BeforeMethode erfolgreich war, ist es wahrscheinlich besser, sie direkt in dieser Methode zu überprüfen. Als Bonus melden mindestens JUnit und TestNG sogar einen anderen Fehler für Fehler von @Before/ @AfterMethoden, sodass festgestellt werden kann, dass das Problem nicht im Test selbst enthalten war.
Sleske
4

So verwende ich die Fail-Methode.

Es gibt drei Zustände, in denen Ihr Testfall enden kann

  1. Bestanden: Die zu testende Funktion wurde erfolgreich ausgeführt und hat die Daten wie erwartet zurückgegeben
  2. Nicht bestanden: Die zu testende Funktion wurde erfolgreich ausgeführt, aber die zurückgegebenen Daten waren nicht wie erwartet
  3. Fehlgeschlagen: Die Funktion wurde nicht erfolgreich ausgeführt und dies war nicht der Fall

beabsichtigt (im Gegensatz zu negativen Testfällen, bei denen eine Ausnahme erwartet wird).

Wenn Sie Eclipse verwenden, werden drei Zustände durch eine grüne, blaue und rote Markierung angezeigt.

Ich verwende die Fehleroperation für das dritte Szenario.

Beispiel: public Integer add (Ganzzahl a, Ganzzahl b) {Neue Ganzzahl zurückgeben (a.intValue () + b.intValue ())}

  1. Bestandener Fall: a = neuer Interger (1), b = neuer Integer (2) und die zurückgegebene Funktion 3
  2. Nicht bestanden Fall: a = neue Interger (1), b = neue Ganzzahl (2) und die Funktion hat einen anderen Soem-Wert als 3 zurückgegeben
  3. Fehlgeschlagener Fall: a = null, b = null und die Funktion löst eine NullPointerException aus
user3044364
quelle
1
Wenn Sie sich den Quellcode von JUnit ansehen, werden Sie feststellen, dass Assertions verwendet werden fail().
Daniel C. Sobral
3

Ich benutze fail()zum Beispiel, um Tests anzuzeigen, die noch nicht abgeschlossen sind (es passiert); Andernfalls würden sie sich als erfolgreich erweisen.

Dies liegt möglicherweise daran, dass mir keine unvollständige () Funktionalität bekannt ist, die in NUnit vorhanden ist.

Alen Siljak
quelle
2

In gleichzeitigen und / oder asynchronen Einstellungen möchten Sie möglicherweise überprüfen, ob bestimmte Methoden (z. B. Delegaten, Ereignis-Listener, Antworthandler, wie Sie es nennen) nicht aufgerufen werden. Abgesehen von spöttischen Frameworks können Sie fail()diese Methoden aufrufen , um die Tests nicht zu bestehen. Abgelaufene Zeitüberschreitungen sind in solchen Szenarien eine weitere natürliche Fehlerbedingung.

Beispielsweise:

final CountDownLatch latch = new CountDownLatch(1);

service.asyncCall(someParameter, new ResponseHandler<SomeType>() {
    @Override
    public void onSuccess(SomeType result) {
        assertNotNull(result);
        // Further test assertions on the result
        latch.countDown();
    }

    @Override
    public void onError(Exception e) {
        fail(exception.getMessage());
        latch.countDown();
    }
});

if ( !latch.await(5, TimeUnit.SECONDS) ) {
    fail("No response after 5s");
}
Raphael
quelle
0

Der wichtigste Anwendungsfall ist wahrscheinlich die Ausnahmeprüfung.

Während junit4 das erwartete Element enthält, um zu überprüfen, ob eine Ausnahme aufgetreten ist, scheint es nicht Teil des neueren junit5 zu sein. Ein weiterer Vorteil der Verwendung fail()gegenüber expectedist, dass Sie es mit finallyder Bereinigung von Testfällen kombinieren können .

dao.insert(obj);
try {
  dao.insert(obj);
  fail("No DuplicateKeyException thrown.");
} catch (DuplicateKeyException e) {
  assertEquals("Error code doesn't match", 123, e.getErrorCode());
} finally {
  //cleanup
  dao.delete(obj);
}

Wie in einem anderen Kommentar erwähnt. Es klingt auch vernünftig, wenn ein Test fehlschlägt, bis Sie die Implementierung abgeschlossen haben.

Udo Held
quelle