Java Mockito Verify:在Verify()期间验证,而不是在mock方法调用期间验证

Java Mockito Verify:在Verify()期间验证,而不是在mock方法调用期间验证,java,junit,mockito,verify,Java,Junit,Mockito,Verify,我使用对象列表调用一个方法performation,并对其进行验证。调用此方法后,我修改了一些“对象” Mockito验证失败,因为参数不匹配(显示修改过的对象),但我可以在调试模式下看到对象在需要时是正确的 理想情况下,这不应该发生,因为应该根据实际调用方法的时间应用verify。验证是否在测试方法中的验证调用期间应用,而不是在模拟方法调用时应用 测试班 @Test public void test() throws Exception { List<ABC> object

我使用对象列表调用一个方法performation,并对其进行验证。调用此方法后,我修改了一些“对象”

Mockito验证失败,因为参数不匹配(显示修改过的对象),但我可以在调试模式下看到对象在需要时是正确的

理想情况下,这不应该发生,因为应该根据实际调用方法的时间应用verify。验证是否在测试方法中的验证调用期间应用,而不是在模拟方法调用时应用

测试班

@Test
public void test() throws Exception {
    List<ABC> objects = new ArrayList<ABC>();
    //populate objects.
    activity.performActions(objects);               
    verify(activity, times(1)).doActivity(objects);
}

verify
比较调用
verify
时的参数内容,而不是调用mock方法时的参数内容。如果修改了列表的内容,则验证将使用修改后的值


另一种方法是使用
答案
在调用该方法后立即检查参数,或者您可以创建一个新列表,而不是修改旧列表。

以前曾询问过此问题-在

当您调用一个已被Mockito存根的方法时,Mockito将存储传递给它的参数,以便以后可以使用
verify
。也就是说,它存储对象引用,而不是对象本身的内容。如果以后更改了这些对象的内容,则
verify
调用会将其参数与更新的对象进行比较-它不会生成原始对象的深度副本

如果需要验证对象的内容,则需要

  • 在方法调用时自己存储它们;或
  • 在方法调用时验证它们

正确的方法是使用Mockito
答案
。因此,对于第二个选项,您将创建一个执行验证的
Answer
,如果参数值不正确,则抛出一个
AssertionFailedError
;不要在测试结束时使用
验证

现在可以使用ArgumentCaptor解决此问题

@Test
public void test() throws Exception {
    List<ABC> objects = new ArrayList<ABC>();
    ArgumentCaptor<List<ABC> objectsCaptor = ArgumentCaptor<List.class>;
    //populate objects.
    activity.performActions(objects);               
    verify(activity, times(1)).doActivity(objectsCaptor.capture());
}
@测试
public void test()引发异常{
列表对象=新的ArrayList();

ArgumentCaptor将代码还原为再现问题的最短示例,粘贴此示例的完整代码以及您得到的准确完整的错误消息。@jbnite修改了问题。您使用的是什么Java?答案似乎不适用于
Java 8
,至少对于复杂对象是如此。
Argument(s) are different! Wanted:
activity.doActivity(
.......
......
@Test
public void test() throws Exception {
    List<ABC> objects = new ArrayList<ABC>();
    ArgumentCaptor<List<ABC> objectsCaptor = ArgumentCaptor<List.class>;
    //populate objects.
    activity.performActions(objects);               
    verify(activity, times(1)).doActivity(objectsCaptor.capture());
}