在测试和要测试的方法中使用相同的值

时间:2014-03-26 15:34:39

标签: java unit-testing junit tdd mockito

要测试的方法:

public boolean isValidStudent(String fName, String lName){
    Student student = new Student(fName, lName);//-----------this creates problem
    return (studentDao.get(student).isEmpty())?false : true;        
}

以下测试失败,因为方法存根总是返回一个空列表,当我专门指定它以返回我创建的列表时。 看来测试中的学生对象和方法是不同的。我能做些什么才能让它发挥作用?我通过在下面的第二种方法中更改方法签名来解决这个问题。但我想在不改变方法的情况下做到这一点。

@Mock
Service service;

@Test
public void isValidStudent(){
    studentList = new ArrayList<Student>();
    studentList.add(new Student());
    studentList.add(new Student());

    Student student = new Student("Tom", "Clancy");//---this creates problem. 

    when(studentDao.get(student)).thenReturn(studentList);
    assertTrue(service.isValidStudent("Tom", "Clancy"));
}

有效的第二种方法:

在这种方法中,我改变了方法签名以接受学生对象而且它工作正常。我只在测试中实例化一次学生对象,并将其用于方法存根,并将其传递给测试中的方法。

public boolean isValidStudent(Student student){
    return (studentDao.get(student).isEmpty())?false : true;        
}

@Mock
Service service;

@Test
public void isValidStudent(){
    studentList = new ArrayList<Student>();
    studentList.add(new Student());
    studentList.add(new Student());

    Student student = new Student("Tom", "Clancy");

    when(studentDao.get(student)).thenReturn(studentList);
    assertTrue(service.isValidStudent(student));
}

1 个答案:

答案 0 :(得分:2)

假设:您的Student班级没有实施.equals() / .hashCode()

默认情况下,when()模拟一个方法调用,mockito会检查它的参数.equals()是否已经将它作为(一个)参数传递给了模拟方法。

但是,如果您没有实施.equals(),那么您将遇到以下情况:

final Student s1 = new Student("foo", "bar");
final Student s2 = new Student("foo", "bar");
s1.equals(s2); // <--- FALSE!

这就是这里发生的事情。在您的第一个场景中,您创建一个Student,对您而言,逻辑相等,但这不是Mockito想要的。因此,在您的第一个方案中,.get()将返回null

然而,在你的第二个中,你传递相同的参考;由于您未实施.equals()Object&#39; .equals().equals()实施,obj1.equals(obj2) if {only} only如果obj1 == obj2 - 就是这种情况。继续上面的代码,在你的情况下:

s1 == s2; // FALSE! (as in first test)
s1 == s1; // true   (as in second test)

如果你想要更多&#34;松散&#34;为了争论,你必须编写自定义参数匹配器; Mockito也可以这样做(借助于它的Hamcrest依赖)。

所有这些戏弄都说你应该通过Student班级实施.equals() / .hashCode()来解决问题。