当前位置: 首页 > 知识库问答 >
问题:

未完成验证,在编写JUnit测试用例时缺少验证(mock)的方法调用

连翰
2023-03-14

我正在面对

org.mockito.exceptions.misusing.UnfinishedVerificationException: 
Missing method call for verify(mock) here:
-> at systemservice.test1.SysParamsBuilderTest.testBuildProcessingInfoIf3(SysParamsBuilderTest.java:241)

我已经检查了所有参数和要传递以验证的对象,但无法找出导致上述异常的原因

我要测试的条件,

if( request.getProcessType() == IPRequest.IPREQUEST_TYPE_DE )
{

     LookInfoIf rdr = new MCLLookInfoReader();

    String origAnatomy = accessor.getValue(AttributeRepNames.ANATOMY_INFO.getTagName());
    String origView = accessor.getValue(AttributeRepNames.VIEW_INFO.getTagName());
    String origPatSize = accessor.getValue(AttributeRepNames.PATIENT_SIZE.getTagName());
    String mclPatSize = getMclPatientSize(origPatSize);
    String boneLook = rdr.getDefaultLook(origAnatomy,origView,core.MCLConstants.IMAGETYPEBONETAG,mclPatSize);
    String tissueLook = rdr.getDefaultLook(origAnatomy,origView,core.MCLConstants.IMAGETYPESOFTTISSUETAG,mclPatSize);

    params.setProcessingLookBone(boneLook);
    params.setProcessingLookTissue(tissueLook);
        params.setAnatomy(origAnatomy);
        params.setView(origView);
        params.setPatientSize(origPatSize);

}

测试用例

@Test
    public void testBuildProcessingInfoIf3() throws Exception
    {
        IPRequest req=new IPRequest(1);//value of IPRequest.IPREQUEST_TYPE_DE

        IPSysParams iPSysParams = Mockito.mock(IPSysParams.class);
        PowerMockito.whenNew(IPSysParams.class).withNoArguments().thenReturn(iPSysParams);

        TagAccessor accessor=Mockito.mock(TagAccessor.class);

        MCLLookInfoReader rdr=Mockito.mock(MCLLookInfoReader.class);
        PowerMockito.whenNew(MCLLookInfoReader.class).withNoArguments().thenReturn(rdr);

        Mockito.when(accessor.getValue(AttributeRepNames.ANATOMY_INFO.getTagName())).thenReturn("ANATOMY_INFO");
        Mockito.when(accessor.getValue(AttributeRepNames.VIEW_INFO.getTagName())).thenReturn("VIEW_INFO");
        Mockito.when(accessor.getValue(AttributeRepNames.PATIENT_SIZE.getTagName())).thenReturn("PATIENT_SIZE");
        Mockito.when(rdr.getDefaultLook("ANATOMY_INFO","VIEW_INFO",core.MCLConstants.IMAGETYPEBONETAG,"All")).thenReturn("boneLook");
        Mockito.when(rdr.getDefaultLook("ANATOMY_INFO","VIEW_INFO",core.MCLConstants.IMAGETYPESOFTTISSUETAG,"All")).thenReturn("tissueLook");

        sysParamsBuilder.buildProcessingInfo(req, info);

        String origAnatomy=accessor.getValue(AttributeRepNames.ANATOMY_INFO.getTagName());
        assertEquals("ANATOMY_INFO",origAnatomy);

        String origView=accessor.getValue(AttributeRepNames.VIEW_INFO.getTagName());
        assertEquals("VIEW_INFO",origView);

        String origPatSize=accessor.getValue(AttributeRepNames.PATIENT_SIZE.getTagName());
        assertEquals("PATIENT_SIZE",origPatSize);

        PowerMockito.verifyPrivate(sysParamsBuilder).invoke("getMclPatientSize",origPatSize);//line 241

        String boneLook=rdr.getDefaultLook("ANATOMY_INFO","VIEW_INFO",core.MCLConstants.IMAGETYPEBONETAG,"All");
        assertEquals("boneLook",boneLook);

        String tissueLook=rdr.getDefaultLook("ANATOMY_INFO","VIEW_INFO",core.MCLConstants.IMAGETYPESOFTTISSUETAG,"All");
        assertEquals("tissueLook",tissueLook);

        Mockito.verify(iPSysParams).setProcessingLookBone(boneLook);//line 244
        Mockito.verify(iPSysParams).setProcessingLookTissue(tissueLook);

        // fill the Anatomy View accrodingly
        Mockito.verify(iPSysParams,Mockito.times(1)).setAnatomy(origAnatomy);
        Mockito.verify(iPSysParams).setView(origView);
        Mockito.verify(iPSysParams).setPatientSize(origPatSize);

    }

堆栈跟踪

org.mockito.exceptions.misusing.UnfinishedVerificationException: 
Missing method call for verify(mock) here:
-> at systemservice.test1.SysParamsBuilderTest.testBuildProcessingInfoIf3(SysParamsBuilderTest.java:241)

Example of correct verification:
    verify(mock).doSomething()

Also, this error might show up because you verify either of: final/private/equals()/hashCode() methods.
Those methods *cannot* be stubbed/verified.

    at systemservice.test1.SysParamsBuilderTest.testBuildProcessingInfoIf3(SysParamsBuilderTest.java:244)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
    at java.lang.reflect.Method.invoke(Unknown Source)
    at org.junit.internal.runners.TestMethod.invoke(TestMethod.java:66)
    at org.powermock.modules.junit4.internal.impl.PowerMockJUnit44RunnerDelegateImpl$PowerMockJUnit44MethodRunner.runTestMethod(PowerMockJUnit44RunnerDelegateImpl.java:310)
    at org.junit.internal.runners.MethodRoadie$2.run(MethodRoadie.java:86)
    at org.junit.internal.runners.MethodRoadie.runBeforesThenTestThenAfters(MethodRoadie.java:94)
    at org.powermock.modules.junit4.internal.impl.PowerMockJUnit44RunnerDelegateImpl$PowerMockJUnit44MethodRunner.executeTest(PowerMockJUnit44RunnerDelegateImpl.java:294)
    at org.powermock.modules.junit4.internal.impl.PowerMockJUnit44RunnerDelegateImpl$PowerMockJUnit44MethodRunner.runBeforesThenTestThenAfters(PowerMockJUnit44RunnerDelegateImpl.java:282)
    at org.junit.internal.runners.MethodRoadie.runTest(MethodRoadie.java:84)
    at org.junit.internal.runners.MethodRoadie.run(MethodRoadie.java:49)
    at org.powermock.modules.junit4.internal.impl.PowerMockJUnit44RunnerDelegateImpl.invokeTestMethod(PowerMockJUnit44RunnerDelegateImpl.java:207)
    at org.powermock.modules.junit4.internal.impl.PowerMockJUnit44RunnerDelegateImpl.runMethods(PowerMockJUnit44RunnerDelegateImpl.java:146)
    at org.powermock.modules.junit4.internal.impl.PowerMockJUnit44RunnerDelegateImpl$1.run(PowerMockJUnit44RunnerDelegateImpl.java:120)
    at org.junit.internal.runners.ClassRoadie.runUnprotected(ClassRoadie.java:34)
    at org.junit.internal.runners.ClassRoadie.runProtected(ClassRoadie.java:44)
    at org.powermock.modules.junit4.internal.impl.PowerMockJUnit44RunnerDelegateImpl.run(PowerMockJUnit44RunnerDelegateImpl.java:122)
    at org.powermock.modules.junit4.common.internal.impl.JUnit4TestSuiteChunkerImpl.run(JUnit4TestSuiteChunkerImpl.java:104)
    at org.powermock.modules.junit4.common.internal.impl.AbstractCommonPowerMockRunner.run(AbstractCommonPowerMockRunner.java:53)
    at org.powermock.modules.junit4.PowerMockRunner.run(PowerMockRunner.java:53)
    at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:50)
    at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:459)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:675)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:382)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:192)

我用同样的方法做了其他测试用例,它已经工作了,但是我不知道为什么它在这里不起作用,而且所有的方法都是公开的。请帮我弄清楚,谢谢

共有3个答案

山煜祺
2023-03-14

从错误消息中:

可能会出现错误,因为您验证了以下方法之一:final/private/equals()/hashCode()。这些方法无法存根/验证。

所以检查一下这些方法

    Mockito.verify(iPSysParams).setProcessingLookBone(boneLook);
    Mockito.verify(iPSysParams).setProcessingLookTissue(tissueLook);
    Mockito.verify(iPSysParams,Mockito.times(1)).setAnatomy(origAnatomy);
    Mockito.verify(iPSysParams).setView(origView);
    Mockito.verify(iPSysParams).setPatientSize(origPatSize);

是最终版本。

董翰墨
2023-03-14

我不理解这里的mockito错误;但我的回答是另一个方向:不要这样验证。

您在这里遵循一种几乎相反的模式:您希望对生产代码中发生的几乎每一个调用都使用mocking/验证。这意味着生产代码中的细微变化总是会直接影响您的单元测试。即使您的方法的“契约”保持不变,当您使用这种验证风格时,您的单元测试也会很快中断。

我的建议是:不必验证对象是否看到大量setter调用,您可以按照以下方式执行操作:

Params expectedParams = ... 
Params actualParams = underTest.whatever();
assertThat(actualParams, is(expectedParams));

如果简单的“equals”检查hamcrestis匹配器在这里不起作用;您仍然可以创建自己的匹配器。

换句话说:不要在单元测试中“微观管理”生产代码。

专注于编写允许测试的代码,而不关心内部的工作方式。相反,检查方法生成的“输出”!

示例:假设您像上面所做的那样对一些params对象进行所有模拟验证;但最后,您的方法返回其他一些params对象。。。那么您的单元测试可能通过了;但是整个方法都是错误的,因为它给了你错误的结果。

燕野
2023-03-14

从异常消息中,问题是这一行:

PowerMockito.verifyPrivate(sysParamsBuilder).invoke("getMclPatientSize",origPatSize);//line 241

使用google搜索powermockito verifyprivate not working,我发现以下页面:https://groups.google.com/forum/#哦!主题/powermock/CEdP24sb\U HY

简而言之,如果您想使用PowerMockito监视您的对象,那么您不能这样做

    SysParamsBuilder sysParamsBuilder = Mockito.spy(new SysParamsBuilder(...));

相反,你需要

    SysParamsBuilder sysParamsBuilder = PowerMockito.spy(new SysParamsBuilder(...));

否则,如果您尝试使用PowerMockito验证私有方法调用,您将看到异常。

 类似资料:
  • 我正在尝试做一个测试,它验证(使用Mockito v1.9.5的)在执行传递

  • 我想在调用doSomething()时验证是否调用过一次someMethod。在doSomething()中,正在调用currentTimeMillis(),该值将不完全相同。我如何测试这个? 当前我收到以下错误消息: *org.mockito.exceptions.misusing.未完成验证例外: 此处缺少验证(模拟)的方法调用:- 正确验证示例:验证(模拟)。doSomething()* B

  • 我是java新手,我正在编写一个ATM程序,用户可以输入三次pin码,如果他们输入的pin码不正确,他们的卡就会被阻塞。我曾尝试为以下代码编写Junit测试,但似乎无法理解。我有两门课,分别是AtmPin和AtmTester。AtmTester是主类所在的位置。 AtmPin.java AtmTester.java

  • 在测试中,我使用的是mockobject: 我试图验证其方法的使用: 但它抛出以下异常: 组织。莫基托。例外情况。滥用。UnfinishedVerificationException:此处缺少验证(模拟)的方法调用: 这一行的例外点是: setMaxRows接受一个int。 当我注释掉这一行时,测试成功了。调试程序时,我可以看到正在设置的setMaxRows方法: BrandLabels是一个Li

  • 问题内容: 我要求在通用api模块(多模块项目)中,我不能使用任何形式的hibernate的验证注释,因此我确实使用了javax.validation中的一个可接受的注释。 当我要验证包含NotBlank批注的域对象(我使用vaadin)时,问题就开始了。我得到以下异常 验证通过调用进行 相同的代码与hibernate的NotBlank完美配合 javax的@Size @NotNull也可以正常工

  • 但这将返回以下错误: org.mockito.exceptions.misusing.NotaMockException: 传递给verify()的参数类型为$proxy4,不是mock!