WrongTypeOfReturnValue Ausnahme geworfen, wenn unit Tests mit mockito

Mein Test

List<Person> myList;

@Test
public void testIsValidPerson() {
    myList = new ArrayList<Person>();

    myList.add(new Person("Tom"));
    when(personDao.get(person)).thenReturn(myList);
    when((personDao.get(person)).isEmpty()).thenReturn(false);//------Exception thrown 

    boolean result = service.isValid("Tom");
    assertFalse(result);
}

Methode getestet werden:

public boolean isValid(String person){
    personDao = new PersonDao();
    Person personObj = new Person(person);
    return (personDao.get(person).isEmpty())?false : true;      
}

Ausnahme geworfen:

org.mockito.exceptions.misusing.WrongTypeOfReturnValue: 
Boolean cannot be returned by get()
get() should return List
***
If you're unsure why you're getting above error read on.
Due to the nature of the syntax above problem might occur because:
1. This exception *might* occur in wrongly written multi-threaded tests.
   Please refer to Mockito FAQ on limitations of concurrency testing.
2. A spy is stubbed using when(spy.foo()).then() syntax. It is safer to stub spies - 
   - with doReturn|Throw() family of methods. More in javadocs for Mockito.spy() method.

Mein Zweiter Ansatz mit spy:

public void testIsValidPerson() {
    myList = new ArrayList<Person>();

    myList.add(new Person("Tom"));
    when(personDao.get(person)).thenReturn(myList);

    List<Person> mylist = personDao.get(person);
    List spy = spy(mylist);

    doReturn(false).when(spy.isEmpty());//------exception thrown

    boolean result = service.isValid("Tom");
    assertFalse(result);
}

Dieser gibt mir folgende Ausnahme:

org.mockito.exceptions.misusing.UnfinishedStubbingException: 
Unfinished stubbing detected here:
-> at com.PersonTest.testIsValid(PersonTest.java:76)

E.g. thenReturn() may be missing.
Examples of correct stubbing:
    when(mock.isOk()).thenReturn(true);
    when(mock.isOk()).thenThrow(exception);
    doThrow(exception).when(mock).someVoidMethod();
Hints:
 1. missing thenReturn()
 2. you are trying to stub a final method, you naughty developer!

Dritten Programm:

@Test
public void testIsValidPerson() {
    myList = new ArrayList<Person>();

    myList.add(new Person("Tom"));
    when(personDao.get(person)).thenReturn(myList);

    boolean result = service.isValid("Tom");//--------Throws null pointer exception
    assertFalse(result);
}

public boolean isValid(String person){
    personDao = new PersonDao();
    Person personObj = new Person(person);
    return (personDao.get(person).isEmpty())?false : true;  //----throws NPE    
}

Vierter Ansatz: wirft Null-Zeiger-Ausnahme

@Test
public void testIsValidPerson() {
    List<Person> mockedList = mock(List.class);
    when(personDao.get(person)).thenReturn(mockedList);
    when(personDao.get(person)).isEmpty().thenReturn(false);
    boolean result = service.isValid("Tom");//--------Throws null pointer exception
    assertFalse(result);
}

public boolean isValid(String person){
    personDao = new PersonDao();
    Person personObj = new Person(person);
    return (personDao.get(person).isEmpty())?false : true;  //----throws NPE    
}

Fünften Ansatz: gibt Auch NPE.

Die get-Methode der interface personDao auf die Datenbank zugreift und die NPE geworfen wird, wenn eine Verbindung zu der DB. Aber es nicht geben NPE beim ersten mal, wenn ich eine leere Liste zurück. Ich bekomme NPE im zweiten Anruf von service.isValid()

@Test
public void testIsValidPerson() {
    when(personDao.get(person)).thenReturn(new ArrayList<Person>());
    List tempList=personDao.get(person);//----I get empty tempList---No NPE
    boolean result = service.isValid("Tom");//--------Throws null pointer exception
    assertFalse(result);
}

Ansatz 6:

@Test
public void testIsValid() {
    personList = new ArrayList<Person>();
    Person person = new Person("Tom");
    personList.add(person);
    when(personDao.get(person)).thenReturn(personList);//-------Uses same person object

    boolean result = service.isValid(person);//------------Uses same person object
    assertTrue(result);
}

Und ich änderte meine Signatur der Methode aus(so dass der test und die zu testende Methode verwenden würde, den gleichen Wert).

public boolean isValid(String name)

zu

public boolean isValid(Person person)
Warum wollen Sie zu verspotten oder Spion einer ArrayList? Sie erstellt eine Liste. Es enthält eine person namens Tom. Also Aufruf von isEmpty() auf der Liste wird false zurückgegeben. Keine Notwendigkeit, zu verspotten oder auszuspionieren, was haben isEmpty() false zurück. Der verspottet DAO gibt die Liste mit Tom. Die service-Aufrufe, die verspottet DAO und somit bekommt die Liste mit Tom. Keine Notwendigkeit, zu verhöhnen, als alles andere.
Ich habe editiert meinen post, der Dritte Ansatz Abschnitt in meinem post. Wenn es das ist was du meinst, ich bekomme NPE, wenn ich das tun.
Sie erhalten NPE, weil der Dienst nicht zu nutzen, die mock-DAO, die Sie erstellt haben, und drückte im test. Es erstellt eine völlig neue PersonDao. Sie brauchen, um passieren die mock-DAO als parameter an den Konstruktor der service. Kurz gesagt, müssen Sie die Verwendung von dependency injection.
Susie, ich bin ein bisschen verwirrt, als was Sie gefragt, und was wollen Sie von einer Antwort jetzt. Sie haben geschrieben, die sechs verschiedene code-snippets - Sie alle geben Sie eine Null-Zeiger-Ausnahme? Sind Sie zufrieden mit meiner Erklärung, warum der fünfte Ansatz funktioniert nicht? Und was passiert mit dem sechsten Ansatz? Es scheint mir, dass es würde wahrscheinlich funktionieren, obwohl ich es noch nicht getestet.

InformationsquelleAutor Susie | 2014-03-24

Schreibe einen Kommentar