使用Mockito </t>创建一个将Class <t>作为参数的方法

时间:2011-03-28 16:29:20

标签: java class generics mocking mockito

有一个通用的方法,它将一个类作为参数,我有问题用Mockito对其进行存根。该方法如下所示:

public <U extends Enum<U> & Error, T extends ServiceResponse<U>> T validate(
    Object target, Validator validator, Class<T> responseClass,
    Class<U> errorEnum);

这太可怕了,至少对我而言......我可以想象没有它的生活,但代码库的其余部分很乐意使用它......

在我的单元测试中,我打算将此方法存根以返回一个新的空对象。但是我如何用mockito做到这一点?我试过了:

when(serviceValidatorStub.validate(
    any(), 
    isA(UserCommentRequestValidator.class), 
    UserCommentResponse.class, 
    UserCommentError.class)
).thenReturn(new UserCommentResponse());

但由于我正在混合匹配匹配器和原始值,我得到“org.mockito.exceptions.misusing.InvalidUseOfMatchersException:参数匹配器的使用无效!”

3 个答案:

答案 0 :(得分:78)

问题是,你不能在模拟调用中混合参数匹配器和真实参数。所以,请做到这一点:

when(serviceValidatorStub.validate(
    any(),
    isA(UserCommentRequestValidator.class),
    eq(UserCommentResponse.class),
    eq(UserCommentError.class))
).thenReturn(new UserCommentResponse());

注意使用eq()参数匹配器来匹配相等。

请参阅:https://static.javadoc.io/org.mockito/mockito-core/1.10.19/org/mockito/Matchers.html#eq(T)

此外,您可以将same()参数匹配器用于Class<?>类型 - 它匹配相同的标识,如== Java运算符。

答案 1 :(得分:2)

只是为了在同一个线程上完成,如果有人想要一个以Class作为参数但不关心类型的方法,或者需要多个类型以相同的方式存根,这里是另一个溶液:

private class AnyClassMatcher extends ArgumentMatcher<Class<?>> {

    @Override
    public boolean matches(final Object argument) {
        // We always return true, because we want to acknowledge all class types
        return true;
    }

}

private Class<?> anyClass() {
    return Mockito.argThat(new AnyClassMatcher());
}

然后致电

Mockito.when(mock.doIt(this.anyClass())).thenCallRealMethod();

答案 2 :(得分:0)

很好的一个@Ash。我使用你的泛型类匹配器来准备下面。 如果我们想要准备一个特定类型的模拟,可以使用它。(不是实例)

private Class<StreamSource> streamSourceClass() {
    return Mockito.argThat(new ArgumentMatcher<Class<StreamSource>>() {

        @Override
        public boolean matches(Object argument) {
            // TODO Auto-generated method stub
            return false;
        }
    });
}

用法:

    Mockito.when(restTemplate.getForObject(Mockito.anyString(), 
            **streamSourceClass(),**
            Mockito.anyObject));