当我运行mockito测试时发生WrongTypeOfReturnValue Exception

con*_*ell 75 java mockito

错误细节:

org.mockito.exceptions.misusing.WrongTypeOfReturnValue: 
Boolean cannot be returned by updateItemAttributesByJuId()
updateItemAttributesByJuId() should return ResultRich
This exception might occur in wrongly written multi-threaded tests.
Please refer to Mockito FAQ on limitations of concurrency testing.
Run Code Online (Sandbox Code Playgroud)

我的代码:

@InjectMocks
protected ItemArrangeManager arrangeManagerSpy = spy(new ItemArrangeManagerImpl());
@Mock
protected JuItemWriteService juItemWriteService;

when(arrangeManagerSpy
    .updateItemAttributes(mapCaptor.capture(), eq(juId), eq(itemTO.getSellerId())))
    .thenReturn(false);
Run Code Online (Sandbox Code Playgroud)

正如你所看到的,我呼吁whenupdateItemAttributes(它返回boolean)不是updateItemAttributesByJuId.

  1. 为什么尝试的Mockito返回一个booleanupdateItemAttributesByJuId
  2. 怎么能纠正这个?

小智 165

根据https://groups.google.com/forum/?fromgroups#!topic/mockito/9WUvkhZUy90,你应该改写你的

when(bar.getFoo()).thenReturn(fooBar)
Run Code Online (Sandbox Code Playgroud)

doReturn(fooBar).when(bar).getFoo()
Run Code Online (Sandbox Code Playgroud)

  • @confusedwindbell如果它解决了你的问题,请考虑将答案标记为已接受. (16认同)
  • 这是一个很好的提示.在使用**@ Aspect**测试一些Spring` @ Repository` DAO方法时,我也遇到了这个问题.如果我做`when(someDao.someMethod()).thenReturn(List <xxx>)`,我得到了这个WrongTypeOfReturnValue异常.通过调试,我可以看到`someMethod`方法实际上是在上面的语句中被调用并触发Around Advice并返回一个`null`但是Mockito期待一个`List <xxx>`. (3认同)
  • 如果要模拟的方法是“static”怎么办? (2认同)
  • @paradocslover在静态的情况下我认为你必须使用 Powermockt Powermock.mockStatic(foo.class) 然后 PowerMockito.when(Foo.class, "method", ...params).thenReturn(bar) (2认同)

juh*_*tio 34

类似错误消息的另一个原因是尝试模拟final方法.不应该试图模拟最终方法(参见最终方法模拟).

我还遇到了多线程测试中的错误.在那种情况下,由gna回答.


rog*_*ack 9

对我来说,这意味着我正在运行:

a = Mockito.mock(SomeClass.class);
b = new RealClass();
when(b.method1(a)).thenReturn(c); 
// within this method1, it calls param1.method2() -- note, b is not a spy or mock
Run Code Online (Sandbox Code Playgroud)

所以发生的事情是,mockito 检测到a.method2()正在调用的,并告诉我我无法ca.method2()哪个错误中返回。

修复:使用doReturn(c).when(b).method1(a)样式语法(而不是when(b.method1(a)).thenReturn(c);),这将帮助您更简洁快速地发现隐藏的错误。

或者在这种特殊情况下,在这样做之后,它开始显示更准确的“NotAMockException”,我将其更改为不再尝试从非模拟对象设置返回值。


Luk*_*uke 8

非常感兴趣的问题。就我而言,这个问题是在我尝试在以下类似行上调试测试时引起的:

Boolean fooBar;
when(bar.getFoo()).thenReturn(fooBar);
Run Code Online (Sandbox Code Playgroud)

重要的注意事项是测试在没有调试的情况下可以正确运行。

无论如何,当我用下面的代码片段替换上面的代码时,我便能够毫无问题地调试问题行。

doReturn(fooBar).when(bar).getFoo();
Run Code Online (Sandbox Code Playgroud)

  • 谢谢,看起来 Kotlin 数据类与字段存在相同的问题,您的解决方案解决了它! (2认同)

not*_*ohn 6

我最近有这个问题。问题是我试图模拟的方法没有访问修饰符。添加public解决了这个问题。


Tza*_*rir 5

我有这个错误,因为在我的测试中我有两个期望,一个在模拟上,一个在具体类型上

MyClass cls = new MyClass();
MyClass cls2 = Mockito.mock(Myclass.class);
when(foo.bar(cls)).thenReturn(); // cls is not actually a mock
when(foo.baz(cls2)).thenReturn();
Run Code Online (Sandbox Code Playgroud)

我通过将 cls 也更改为模拟来修复它