【发布时间】:2015-10-22 09:06:04
【问题描述】:
我遇到了一个非常奇怪的问题。
URL = "/my/specific/url/";
when(this.restHelperMock.post(
eq(myEnum),
eq(this.config.apiEndpoint() + URL),
any(JSONObject.class))).thenReturn(new JSONObject(myDesiredJsonContent));
甚至包含
URL = "/my/specific/url/";
when(this.restHelperMock.post(
eq(myEnum),
contains(this.config.apiEndpoint() + URL),
any(JSONObject.class))).thenReturn(new JSONObject(myDesiredJsonContent));
给我
org.mockito.exceptions.misusing.InvalidUseOfMatchersException:
Invalid use of argument matchers!
0 matchers expected, 1 recorded:
This exception may occur if matchers are combined with raw values:
//incorrect:
someMethod(anyObject(), "raw String");
When using matchers, all arguments have to be provided by matchers.
For example:
//correct:
someMethod(anyObject(), eq("String by matcher"));
For more info see javadoc for Matchers class.
即使我不使用 RAW 表达式。
奇怪的是,如果我将 contains 方法更改为:
URL = "/my/specific/url/";
when(this.restHelperMock.post(
eq(myEnum),
contains(URL),
any(JSONObject.class))).thenReturn(new JSONObject(myDesiredJsonContent));
省略端点,它可以工作。
Config 和 RestHelper 都被模拟了:
this.restHelperMock = mock(RESTHelper.class);
this.config = mock(MyConfiguration.class);
when(this.config.apiEndpoint()).thenReturn("http://host:port/api");
带有 ApiEndpoint 的 URL 等于我想要模拟的 URL, 即使不是这样,我也应该得到一个 NullpointerException,因为虚假模拟。 但是在这里我没有任何想法。
感谢您的回答。
【问题讨论】:
-
你的
contains和eq都来自Mockito,因为即使hamcrest两者都有。 -
我猜问题可能是您在
eq ( ... )调用期间调用了一个模拟方法 (this.config.apiEndpoint())。尝试简单地将完整的 URL 放在那里(host:port/api/my/specific/url)而不是在那里调用另一个模拟,这可能会使 Mockito 感到困惑,因为它依赖于模拟的内部状态 -
@FlorianSchaetz 谢谢,这就是解决方案。我没想到这会发生。你能写一个anwser,我可以接受吗?
-
@FlorianSchaetz
config.apiEndpoint()不应该先评估,然后通过吗?所以eq(...)的参数应该无关,如果源对象来自一个模拟评估,或者一个简单的字符串文字。 -
老实说,我只是在猜测。整个问题可能归结为 Mockito 的一些复杂的固有状态,它阻止了它的工作。也许比我更喜欢 Mockito 的人可以解释这一点。有一天会尝试调试它以找出其他情况。
标签: java junit mocking mockito