Przeprowadzam testy JUnit na dużej bazie kodu i zdałem sobie sprawę, że czasami dostaję „Błędy”, a innym razem otrzymuję „Awarie”. Co za różnica?
Odpowiedzi:
Ok, właśnie zauważyłem wzór i myślę, że go rozgryzłem (popraw mnie, jeśli się mylę). Wydaje mi się, że niepowodzenia są wtedy, gdy zawodzą twoje przypadki testowe - tj. Twoje twierdzenia są niepoprawne. Błędy to nieoczekiwane błędy, które pojawiają się podczas próby rzeczywistego uruchomienia testu - wyjątki itp.
@Test
z expected = SomeException.class
.
Jeśli test zgłasza wyjątek, który nie jest propagowany przez platformę Assertion w Junit, zostanie zgłoszony jako błąd. Na przykład wyjątek NullPointer lub ClassNotFound zgłosi błąd:
String s = null;
s.trim();
lub,
try {
// your code
} catch(Exception e) {
// log the exception
throw new MyException(e);
}
Mimo to następujące osoby zgłoszą awarię:
Assert.fail("Failure here");
lub,
Assert.assertEquals(1, 2);
lub nawet:
throw new AssertionException(e);
To zależy od używanej wersji Junit. Junit 4 rozróżnia awarię od błędu, ale Junit 4 upraszcza to tylko jako awarie.
Poniższy link zawiera bardziej interesujące dane wejściowe:
Z „Pragmatic Unit Testing in Java 8 with JUnit”:
Asercje (lub potwierdzenia) w JUnit to statyczne wywołania metod, które dodajesz do testów. Każde stwierdzenie jest okazją do zweryfikowania, że jakiś warunek jest prawdziwy. Jeśli potwierdzony warunek nie jest spełniony, test zatrzymuje się w tym miejscu, a JUnit zgłasza niepowodzenie testu.
(Jest również możliwe, że gdy JUnit uruchomi Twój test, wyjątek zostanie zgłoszony i nie zostanie przechwycony. W takim przypadku JUnit zgłasza błąd testu).
Skomentowałem linię, która wyrzuca błąd testu i błąd testu.
@Test
public void testErrorVsTestFailure() {
final String sampleString = null;
assertEquals('j', sampleString.charAt(0) );
//above line throws test error as you are trying to access charAt() method on null reference
assertEquals(sampleString, "jacob");
//above line throws Test failure as the actual value-a null , is not equal to expected value-string "jacob"
}
Tak więc Junit wyświetla błąd testu za każdym razem, gdy pojawi się wyjątek, i błąd testu, gdy oczekiwana wartość wyniku nie jest zgodna z rzeczywistą wartością
Klasa źródłowa: JUnitReportReporter.java
public void generateReport(List<XmlSuite> xmlSuites, List<ISuite> suites, String defaultOutputDirectory) {
//......
for (ITestResult tr : (Set) entry.getValue()) {
TestTag testTag = new TestTag();
boolean isSuccess = tr.getStatus() == 1;
if (!(isSuccess)) {
if (tr.getThrowable() instanceof AssertionError)
++errors;
else {
++failures;
}
}
}
Jak widać poniżej w powyższej metodzie
instancja tr.getThrowable () AssertionError
liczba błędów wzrasta, gdy jest to wystąpienie AssertionError, w przeciwnym razie (dowolny Throwable) jest liczony jako awarie.
Masz rację, że awarie pochodzą z AssertionErrors wyrzuconych przez metody asercji JUnit lub przez zgłoszenie błędu AssertionError lub przez zgłoszenie wyjątku, który zadeklarowałeś w swojej @Test
adnotacji, a błędy pochodzą z innych, nieoczekiwanych wyjątków. Ale jest między nimi ważna różnica:
Niepowodzenie oznacza, że test został przeprowadzony poprawnie i zidentyfikował defekt w kodzie.
Błąd może oznaczać błąd w kodzie, ale taki, którego nawet nie testowałeś. Może to również oznaczać, że błąd występuje w samym teście.
Krótko mówiąc, awaria oznacza, że musisz przepisać testowany kod. Błąd oznacza, że może to być test jednostkowy, który musisz przepisać. Może to oznaczać, nawet jeśli błąd wystąpił w Twoim kodzie, na przykład a NullPointerException
, ponieważ wykryłeś lukę, której nawet nie testowałeś, więc warto to sprawdzić.
Paradoksalnie, JUnit i innych ram badań związanych (TestNG, hamcrest) zapewniają assert operacji, które sprawdzają stan i jeśli to się nie powiedzie , wyrzucany jest "pod maską" błąd java.lang.AssertionError, który rozszerza java.lang.Error.
Ale to nie zaprzecza powyższym odpowiedziom, które są oczywiście w pełni aktualne. Aby więc oznaczyć określony przepływ testów jako niepowodzenie, można rzucić AssertionError, jednak nie jestem pewien, czy jest to naprawdę udokumentowane w odpowiednich instrukcjach, ponieważ bardziej odpowiednie jest użycie dedykowanego API fail (). Inne rodzaje broni miotanej będą traktowane jako błędy, a nie awarie.
Zasadniczo niepowodzenia odnoszą się do niespełnionych stwierdzeń, podczas gdy błędy wynikają z nieprawidłowego wykonania testu . i myślę, że każde IDE ma symboliczne ikony z różnymi kolorami oznaczające powodzenie , niepowodzenie i błąd testów.
Aby uzyskać więcej informacji, sprawdź to .
java.lang.AssertionError
rzucony zostanie cokolwiek rozszerzającego , zostanie to pokazane jako niepowodzenie testu zamiast błędu testu. Powinieneś rozważyć zaakceptowanie własnej odpowiedzi, ponieważ jest poprawna.