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

Mockito模拟方法,但使用其参数模拟返回

吕霄
2023-03-14

有一个方法公共内容创建儿童(字符串路径,字符串内容类型,地图

我想用任何类型的参数来模拟该方法,因此when()将不起作用,因为我必须告诉它该方法应该接收哪些参数才能真正模拟。

因此,我想对任何方法调用做出实际反应,而不依赖于它的给定参数(使用spies?)然后调用某种类型的“回调”来返回一个Content对象,我想用给该方法的实际参数来构建它。

我在Mockito中找不到支持此功能的特定API。


共有3个答案

屈星腾
2023-03-14

你可以用匹配器

MyClass m = mock(MyClass.class);
when(m.createChild(any(String.class), any(String.class), any(Map.class))).thenReturn(new Content());

您还应该能够以这种方式使用参数

when(m.createChild(any(String.class), any(String.class), any(Map.class))).thenAnswer(
       new Answer<Content>()
       {
           @Override
           public Content answer(final InvocationOnMock invocation) throws Throwable
           {
               return new Content((String) invocation.getArguments()[0], 
(String) invocation.getArguments()[1],
(Map) invocation.getArguments()[2]);
               }
           }
       }
       );
奚翰海
2023-03-14

当然可以。我已经为此编写了简单的单元测试

public class MockitoTest {


    private SampleService sampleService;

    @Before
    public void setUp() throws Exception {
        sampleService = Mockito.mock(SampleService.class);
    }

    @Test
    public void mockitoTest() throws Exception {
        when(sampleService.createChild(anyString(), anyString(), anyMapOf(String.class, Object.class)))
            .thenAnswer(invocationOnMock -> {
                //Here you can build result based on params
                String pathArg = (String) invocationOnMock.getArguments()[0];
                if (pathArg.equals("p1")) {
                    return new Content("Content for p1");
                } else if (pathArg.equals("p2")) {
                    return new Content("Content for p2");
                } else {
                    return invocationOnMock.callRealMethod();
                }
            });

        Content content = sampleService.createChild("p1", "any", new HashMap<>());
        assertEquals("Content for p1", content.getData());

        content = sampleService.createChild("p2", "any", new HashMap<>());
        assertEquals("Content for p2", content.getData());

        content = sampleService.createChild("whatever", "any", new HashMap<>());
        assertEquals("original", content.getData());

    }

    /**
     * Sample service with method
     */
    private static class SampleService {

        public Content createChild(String path, String contentType, Map<String, Object> properties) {
            return new Content("original");
        }

    }

    /**
     * Content example
     */
    private static class Content {

        private String data;

        Content(String data) {
            this.data = data;
        }

        String getData() {
            return data;
        }
    }

}
陈野
2023-03-14

您可以使用匹配器

您可以尝试以下方法

when(service.createChild(anyString(), anyString(), anyMap()))
     .thenReturn(any(Content.class));
 类似资料:
  • 问题内容: 使用Mockito,有什么方法可以模拟类中的某些方法,而不能模拟其他方法? 例如,在这个(当然是人为设计的)类中,我想模拟和返回值(如下面的测试代码所示),但我想按类中的代码执行乘法 问题答案: 要直接回答你的问题,是的,你可以模拟某些方法而无需模拟其他方法。这称为部分模拟。有关更多信息,请参见Mockito文档。 例如,你可以在测试中执行以下操作: 在这种情况下,除非thenCall

  • 使用mockito模拟一个方法会确保永远不会调用被模拟的方法吗?我有一个主类,它包含一些我想为其编写单元测试的代码,还有一个单元测试类MainTest,它包含主类的单元测试。 eg: 源类: JUnit测试(使用mockito) 这项测试失败了。为什么?

  • 我是莫基托的新手。我试图通过模拟数据库交互为服务编写jnuit: 我有下面的类(只是实际类的代表) 我的测试课就像是 但是当我运行这个测试时,它仍然调用实际的db调用并从DB中检索值,而不是模拟值,我应该模拟sql连接和非默认构造函数吗?我一无所知。 -- 更新 正如人们所建议的那样,我将DAO实例化移动到我的服务构造函数中,并且还使用了Spy,但是我仍然调用了实际的DB调用而不是模拟调用。

  • 我的测试存根是 我在这里做错了什么?

  • 让我向您展示getCurrentWeatherWithForecastUsecase类actgually是什么样子: } //这很容易,它只需要一个天气存储库,并要求它获取结果。我把它发送回调用者,调用者将显示它。 更新: 以下是故障的整个堆栈跟踪: