2013-03-08 15 views
8

Non riesco a capire perché uno dei miei test stia fallendo.JUnit test fallito, sebbene venga lanciata un'eccezione prevista

Ecco il test:

@Test(expected = IllegalArgumentException.class) 
public void complainsIfFromLocIsDifferentObject() throws Throwable { 
    board.set(make(), 1, 3); //Creates different rook from 'piece' 
    assertFalse("ChessPiece Test 2", piece.isValidMove(getValidMove(1, 3), board)); 
} 

Ho impostato un punto di interruzione e passati attraverso il processo più volte. Entra nella seconda istruzione if nella classe ChessPiece e sembra lanciare l'eccezione. Il processo torna quindi alla classe Rook e restituisce false nel blocco super.

Qualche idea su cosa sta succedendo? Grazie

codice Rilevante:

public class Rook extends ChessPiece { 

    @Override 
    public boolean isValidMove(Move m, IChessBoard b) { 
     if (super.isValidMove(m, b) == false) 
      return false; 

     // Add logic specific to rook 
     if(m.fromRow == m.toRow || m.fromColumn == m.toColumn) 
      return true; 
     else 
      return false; 
    } 
} 


public abstract class ChessPiece implements IChessPiece { 

    @Override 
    public boolean isValidMove(Move m, IChessBoard b) { 

     //Verify that there is a piece at the origin 
     if (b.pieceAt(m.fromRow,m.fromColumn) == null) 
      throw new IllegalArgumentException(); 

     // Verify that this piece is located at move origin 
     IChessPiece piece = b.pieceAt(m.fromRow, m.fromColumn); 
     if (this != piece) 
      throw new IllegalArgumentException(); 
    } 
} 
+1

È molto difficile capire cosa sta succedendo da * solo * il codice parziale che hai fornito. Puoi semplificarlo in un breve esempio * completo *? E se ti aspetti 'isValidMove' di lanciare un'eccezione, perché dovresti * anche * avere un'asserzione (che non raggiungerai)? –

+2

Oh, e l'implementazione 'ChessPiece.isValidMove' è un codice non valido - non restituisce nulla. Ciò suggerisce che non stai eseguendo il codice che hai pubblicato. –

+0

Cosa dice il testfailure? –

risposta

3

It goes into the second if-statement in the ChessPiece class, and seems to throw the exception. The process then goes back to the Rook class and returns false under the super block.

cosa accade è la prima riga nella isValidMove() di Rook classe chiama super metodo in modo controllo passa lì, ma a causa della condizione di secondo if non soddisfatta getta IllegalArgumentException e quindi controlla i ritorni alla classe figlio, ad esempio Rook e non è possibile che return false ora abbia generato un'eccezione, pertanto l'eccezione verrà nuovamente generata da questo metodo e verrà nuovamente generata da juni t metodo complainsIfFromLocIsDifferentObject.

Questo sarà compreso dal framework JUnit e dovrebbe superare il test case.

Verificare se si dispone di questa riga @RunWith(value = BlockJUnit4ClassRunner.class) nella classe del caso di test.

UPDATE:

@RunWith(value = BlockJUnit4ClassRunner.class) 
public class Test extends TestCase{ 

    @Test(expected = IllegalArgumentException.class) 
    public void test1() throws Throwable{ 
     assertFalse(throwException()); 
    } 

    private boolean throwException(){ 
     throw new IllegalArgumentException(); 
    } 
} 

Questo banco di prova passa per me.

+0

Non ho @RunWith (BlockJUnit4ClassRunner.class) nella classe case test. Quando lo aggiungo viene visualizzato un errore" L'attributo il valore non è definito per il tipo di annotazione RunWith" cosa è che il tentativo di fare, comunque? – JZachow

+1

' @RunWith (value = BlockJUnit4ClassRunner.class) 'utilizzare questo invece –

+0

questo codice ha funzionato, ma il test non riesce ancora. – JZachow

1

Come si scrive in un commento JUnit ti dice ciò che è sbagliato:

I get "java.lang.AssertionError:Expected exception: java.lang.IllegalArgumentException

si ottiene un AssertionError, probabilmente da un'affermazione prima dell'eccezione prevista si butta o perché l'eccezione viene gestita e poi un'affermazione giustiziati che fallisce.

Se si rimuove il valore 'atteso' dal l'annotazione JUnit vi darà l'esatta posizione in cui l'asserzione non riuscita (aka stacktrace)

0

Di solito io non avevo messo asserzioni JUnit attorno al codice che mi aspetto l'eccezione gettare.

Così

@Test(expected = IllegalArgumentException) 
public void test() { 
    board.set(make(), 1, 3); //Creates different rook from 'piece' 
    piece.isValidMove(getValidMove(1, 3), board); 
} 

caso contrario, l'eccezione viene generata all'interno del assert JUnit che avvolge l'eccezione in un assertionException.