看起来正确的doThrow中的Mockitoexception

我正在尝试模拟一个方法,看看我是否正确处理exception。 这是我得到的。

接口:

interface SampleManager { void deleteVariome(String specimenId, String analysisId) throws Exception; // ... } 

unit testing:

 // ... SampleManger sampleManager = mock(SampleManager.class); // below is line 753 doThrow(Exception.class).when(sampleManager).deleteVariome(sample1.getId(), analysisId); 

结果:

 org.mockito.exceptions.misusing.UnfinishedStubbingException: Unfinished stubbing detected here: -> at ...server.ArchiveManagerImplUTest.deleteVariomeFails(ArchiveManagerImplUTest.java:753) Eg thenReturn() may be missing. Examples of correct stubbing: when(mock.isOk()).thenReturn(true); when(mock.isOk()).thenThrow(exception); doThrow(exception).when(mock).someVoidMethod(); <-- this looks a log like what I did! Hints: 1. missing thenReturn() 2. you are trying to stub a final method, you naughty developer! <-- I have a lot of other mocks of this interface in this test that work. 

从我遇到的一个相同的问题,我怀疑sample是一个模拟,你在其他地方存在sample.getId()吗? 无论如何,这在我的案例中引起了这个问题。

出于某种原因,如果以这种方式传递doThrow一起使用的存根的其中一个参数是您也doThrow的方法的结果,Mockito会感到沮丧。 我不知道,这可能是为了避免无限循环而进行的重新检查。

无论如何,尝试用常量值替换sample.getId() ,这应该可以解决问题。 你可以考虑在你的测试中使用一个常量来模拟它和它的任何进一步用途。 然后,您还可以通过添加另一个要verify调用来verify您正在测试的方法是否使用了sample.getId()

此错误通常在实际发生的位置后报告。 如果你没有正确地存根,Mockito通常无法分辨,直到你下一次调用Mockito方法之一。 这可能是在同一个测试方法中,在同一个类中的后续测试方法,或者甚至是完全不同的测试类。

你引用的那条线对我来说很好看。 看看它上面的线条,你可以称之为Mockito存根或validation方法。 很可能你有一个没有关联的thenReturnthen或者thenThrow 。 或者您可能verify缺少实际的方法调用。 还有其他一些可能性。

如果你在上面引用的那行中找不到错误,那么发布一些你的代码,我会仔细看看。

正如Gijs的答案所述,这可能是由于Mockito的一个错误。 这是一个完整的测试,可以重现它:

 interface Sample { String getId(); } interface SampleManager { void deleteVariome(String specimenId, String analysisId); } @Test public void probableMockitoBug() { Sample sample1 = mock(Sample.class); when(sample1.getId()).thenReturn("a"); SampleManager manager = mock(SampleManager.class); doThrow(Exception.class).when(manager).deleteVariome(sample1.getId(), "b"); manager.deleteVariome("a", "b"); } 

测试产生以下输出:

 org.mockito.exceptions.misusing.UnfinishedStubbingException: 
这里检测到未完成的存根:
 - > at org.mockitousage.JavadocExamplesTest.probableMockitoBug(JavadocExamplesTest.java:404)

例如,返回()可能会丢失。
正确存根的例子:
    当(mock.isOk())thenReturn(真)。
    当(mock.isOk())thenThrow(例外)。
     doThrow(例外)。当(模拟).someVoidMethod();
提示:
  1.缺少返回()
  2.你正在试图找到一个最后的方法,你顽皮的开发人员!

    在org.mockito.exceptions.Reporter.unfinishedStubbing(Reporter.java:55)
    在org.mockito.internal.progress.MockingProgressImpl.validateState(MockingProgressImpl.java:74)
    在org.mockito.internal.progress.ThreadSafeMockingProgress.validateState(ThreadSafeMockingProgress.java:49)
    在org.mockito.internal.MockHandler.handle(MockHandler.java:71)
    在org.mockito.internal.InvocationNotifierHandler.handle(InvocationNotifierHandler.java:36)
     at org.mockito.internal.creation.MethodInterceptorFilter.intercept(MethodInterceptorFilter.java:48)
     at org.mockitousage.JavadocExamplesTest $ Sample $$ EnhancerByMockitoWithCGLIB $$ d5ac41.getId()
     at org.mockitousage.JavadocExamplesTest.probableMockitoBug(JavadocExamplesTest.java:404)
     at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    在org.mockito.internal.runners.JUnit45AndHigherRunnerImpl.run(JUnit45AndHigherRunnerImpl.java:37)
    在org.mockito.runners.MockitoJUnitRunner.run(MockitoJUnitRunner.java:62)

你必须提供Exception.class的一个实例而不是Exception类本身。

 doThrow(new Exception()).when(sampleManager).deleteVariome(sample1.getId(), analysisId); 

编辑好@DavidWallace纠正了我,所以要警告(或者说更开明),因为1.9你可以提供抛出的exception类,它将为你构建一个。

在我的情况下而不是

 doThrow(exception).when(mock).someVoidMethod() 

 doThrow(exception).when(mock.someVoidMethod())