assert vs. JUnit Assertions


85

Oggi ho visto un test case JUnit con un'asserzione java invece delle asserzioni JUnit: ci sono vantaggi o svantaggi significativi nel preferire l'una all'altra?


Esistono differenze di fatto tra le asserzioni JUnit e la parola chiave Java "assert". Questa non è affatto una domanda basata sull'opinione.
Thomas W

Risposte:


95

In JUnit4 l'eccezione (in realtà Error) lanciata da un'asserzione JUnit è la stessa dell'errore generato dalla assertparola chiave java (AssertionError), quindi è esattamente la stessa assertTruee diversa dalla traccia dello stack non si poteva dire la differenza.

Detto questo, le affermazioni devono essere eseguite con un flag speciale nella JVM, facendo apparire molti test superati solo perché qualcuno ha dimenticato di configurare il sistema con quel flag quando sono stati eseguiti i test JUnit - non va bene.

In generale, per questo motivo, direi che usare JUnit assertTrueè la pratica migliore, perché garantisce che il test venga eseguito, assicura coerenza (a volte usi assertThato altre asserzioni che non sono una parola chiave java) e se il comportamento di JUnit afferma dovrebbe cambiare in futuro (come l'aggancio a qualche tipo di filtro o altre funzionalità future di JUnit) il tuo codice sarà in grado di sfruttarlo.

Il vero scopo della parola chiave assert in java è poterla disattivare senza penalità di runtime. Ciò non si applica agli unit test.


26

Preferisco le asserzioni JUnit in quanto offrono un'API più ricca rispetto assertall'istruzione incorporata e, cosa più importante, non è necessario abilitarla esplicitamente a differenza di assert, che richiede l' -eaargomento JVM.


1
-eaè sempre abilitato in mvn test, non è necessario -ea. API più ricca, buona cattura. A volte penso che l'API sia utilizzata in modo improprio in test perché non fa parte dell'applicazione (a in api), preferisco chiamarla solo metodi più ricchi.
Grim

20

Quando un test fallisce ottieni più informazioni.

assertEquals(1, 2); risultati in java.lang.AssertionError: expected:<1> but was:<2>

vs

assert(1 == 2); risultati in java.lang.AssertionError

puoi ottenere ancora più informazioni se aggiungi l'argomento del messaggio a assertEquals


9
provare assert 1==2: "1 is not 2";.
Grim

@PeterRader Prova la parola chiave assert quando -ea non è abilitato. O meglio ancora, usa le asserzioni JUnit che funzionano sempre.
Thomas W

1
@ThomasW quando -ea non è abilitato non è un test. Le asserzioni JUnit non funzionano sempre, funzionano solo se decidi di utilizzare JUnit che cos'è un framework e, in caso di maven, una dipendenza maven, una dipendenza maven che deve essere solo nell'ambito di test. Abbiamo due lati qui: cosa preferisci? 1 ° lato : usa un framework, come dipendenza solo nell'ambito del test, che deve essere scaricato, che eclipse ti consente di utilizzare in classi che non sono nella cartella src / main ma non si compilano lì perché maven ha junit solo in test- ambito o secondo lato : usa le cose incorporate.
Grim

1
@PeterRader Questa domanda riguarda i casi di test JUnit. In quel contesto dovrebbe essere usata JUnit o una classe di asserzione simile, perché sono sempre abilitate. Personalmente sono stato sorpreso dal fatto che la parola chiave Java "assert" non fosse abilitata in passato e non credo che le asserzioni inaffidabili abbiano un posto nel codice di test.
Thomas W

Nel contesto separato delle asserzioni nel codice delle funzionalità - importante per una solida pratica di programmazione, sebbene non sia effettivamente l'argomento della domanda - sia Spring che Google Guava hanno classi di asserzioni che sono sempre abilitate. Raccomando un uso generoso di questi come parametri e condizioni preliminari per garantire la correttezza. Oltre a ciò, nelle aree critiche per le prestazioni, può esserci una piccola area in cui Java assertpuò essere preferibile - per i controlli di correttezza che avrebbero un impatto sulle prestazioni e quindi sono meglio disabilitati per impostazione predefinita. Tuttavia, la mia esperienza è che la maggior parte delle affermazioni dovrebbe essere sempre attiva.
Thomas W,

8

Direi che usa JUnit asserisce nei casi di test e usa java assert nel codice. In altre parole, il codice reale non dovrà mai avere dipendenze JUnit, come ovvio, e se è un test, dovrebbe usare le sue variazioni JUnit, mai l'assert.


0

Direi che se stai usando JUnit dovresti usare le asserzioni JUnit. assertTrue()è fondamentalmente lo stesso di assert, altrimenti perché usare anche JUnit?


4
Usereste JUnit per il framework di esecuzione di test. Le affermazioni sono davvero una piccola parte del valore che JUnit ti dà. JUnit senza Assertrichiederebbe più boilerplate. assertsenza JUnit richiederebbe di scrivere un intero framework.
Yishai

1
Stavo più dicendo che se hai intenzione di utilizzare lo strumento, USA LO STRUMENTO. le vecchie affermazioni regolari sembrano un po 'sciocche nei casi di test di JUnit. A mio parere appartengono al codice attuale.
CheesePls

1
@CheesePls "regolari vecchie dichiarazioni di asserzione" sono infatti più recenti di quanto asserisce JUnit.
dolmen

0

Questo potrebbe non essere applicabile se usi esclusivamente cose nuove e brillanti, ma assert non è stato introdotto in Java fino alla 1.4SE. Pertanto, se devi lavorare in un ambiente con una tecnologia precedente, potresti propendere per JUnit per motivi di compatibilità.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.