Java 如何模拟影响对象的void返回方法
我正在为我的应用程序编写单元测试,我想知道Mockito框架是否可能影响传递到返回模拟类void的方法中的对象。例如,调用一个模拟验证类,该类包含一个返回void但通过作为参数传入的对象跟踪各种更改和元数据的方法Java 如何模拟影响对象的void返回方法,java,mockito,Java,Mockito,我正在为我的应用程序编写单元测试,我想知道Mockito框架是否可能影响传递到返回模拟类void的方法中的对象。例如,调用一个模拟验证类,该类包含一个返回void但通过作为参数传入的对象跟踪各种更改和元数据的方法 public GetCartItemsOutput getCartItems(GetCartItemsInput getCartItemsInput) { CartItemsFilter cartItemsFilter = new CartItemsFilter();
public GetCartItemsOutput getCartItems(GetCartItemsInput getCartItemsInput) {
CartItemsFilter cartItemsFilter = new CartItemsFilter();
validator.validateCartItemsInput(getCartItemsInput, cartItemsFilter); ...
我在其他测试中模拟了validator类,但在这次测试中,我需要模拟对cartItemsFilter对象的更改,我不知道该怎么做。答案是可以的,根据测试的需要,基本上有两个级别 如果您只想测试与模拟对象的交互,您可以简单地使用该方法来验证是否调用了void方法 如果测试确实需要模拟对象修改传递给它的参数,则需要实现: 编辑以显示使用带无效方法的答案的正确形式
doAnswer(new Answer() {
@Override
Object answer(InvocationOnMock invocation) {
Object[] args = invocation.getArguments();
((MyClass)args[0]).myClassSetMyField(NEW_VALUE);
return null; // void method, so return null
}
}).when(mock).someMethod();
在Java 8+中,使用lambda简化了上述内容:
doAnswer(invocation-> {
Object[] args = invocation.getArguments();
((MyClass)args[0]).myClassSetMyField(NEW_VALUE);
return null;
}).when(mock).someMethod();
ArgumentCaptor也可能会有所帮助 以下是从中找到的片段:
ArgumentCaptor argument=ArgumentCaptor.forClass(GetCartItemsInput.class);
验证(mock).getCartItems(argument.capture());
assertEquals(cartItemsFilter,argument.getValue());
要补充凯文·韦尔克的答案,
如果您的MyClass是一个自定义类,那么在其中定义一个equals/hashcode方法,以便Mockito可以使用它精确匹配方法调用
在我的例子中,“MyClass”在第三方API中,因此我必须使用下面的方法“any”——
doAnswer(new Answer() {
Object answer(InvocationOnMock invocation) {
Object[] args = invocation.getArguments();
((MyClass)args[0]).myClassSetMyField(NEW_VALUE);
return null; // void method, so return null
}
}).when(mock).someMethod(any(MyClass.class));
这并不能解决op的问题,他需要回答谢谢你的帮助。我花了一段时间思考“((MyClass)args[0]).myClassSetMyField(NEW_VALUE);”,但最终我发现关键是设置传入模拟方法的参数。再说一遍,泰。
doAnswer(new Answer() {
Object answer(InvocationOnMock invocation) {
Object[] args = invocation.getArguments();
((MyClass)args[0]).myClassSetMyField(NEW_VALUE);
return null; // void method, so return null
}
}).when(mock).someMethod(any(MyClass.class));