将仿制药与Mockito匹配 [英] Match generics with Mockito

查看:104
本文介绍了将仿制药与Mockito匹配的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试模拟Spring Rest的restTemplate.exchange方法.

I'm trying to mock the restTemplate.exchange method of Spring Rest.

在同一测试中,我有多个调用,它们的区别仅在于返回类型.

In the same test I have multiple calls which differ only by the return type.

以下是我创建的模拟的方法

Here are the methods with the mocks I created

第一

// Original method
restTemplate.exchange(UrlMap.SEARCH + '?' + searchDocsForm.toQueryParams(),
            HttpMethod.GET, null, new ParameterizedTypeReference<SearchResultsDTO<SolrDocumentDTO>>() {
            })
// Mock
when(restTemplate.exchange(any(String.class), any(HttpMethod.class), any(), Matchers.<ParameterizedTypeReference<SearchResultsDTO<SolrDocumentDTO>>>any())).thenReturn(
            new ResponseEntity<>(searchResultsDTO, HttpStatus.OK));

第二

// Original method
restTemplate.exchange(UrlMap.ALL_DOCUS_TOPICS,
            HttpMethod.GET, null, new ParameterizedTypeReference<List<SelectItem>>() {
            }).getBody();
// Mock
when(restTemplate.exchange(any(String.class), any(HttpMethod.class), any(), Matchers.<ParameterizedTypeReference<List<SelectItem>>>any())).thenReturn(
            new ResponseEntity<>(selectItems, HttpStatus.OK));

模拟不考虑ParameterizedTypeReference的通用参数,最后定义的模拟胜过前者.

The generic parameters of ParameterizedTypeReference are not considered by the mock, and the last defined mock wins over the former.

有什么办法可以使它工作?

Is there any way to make it work?

推荐答案

Mockito不能很好地匹配泛型本身,但是您的解决方案比一般情况要容易得多.

Mockito isn't good at matching generics itself, but your solution is much easier than the general case.

替换您的

Matchers.<ParameterizedTypeReference<SearchResultsDTO<SolrDocumentDTO>>>any())

具有:

eq(new ParameterizedTypeReference<SearchResultsDTO<SolrDocumentDTO>>() {}))


首先,Matchers.any()与类型不匹配,甚至与any(Foo.class)类型也不匹配(从Mockito 1.x开始). any()匹配所有值,包括null 并包括错误的类型:


First of all, Matchers.any() doesn't match type, not even in its any(Foo.class) variety (as of Mockito 1.x). any() matches all values, including null and including incorrect types:

匹配任何对象,包括null

Matches any object, including nulls

此方法不使用给定参数进行类型检查,仅在此位置使用,以避免强制转换代码.但是,这可能会在将来的主要版本中更改(可以添加类型检查).

This method doesn't do type checks with the given parameter, it is only there to avoid casting in your code. This might however change (type checks could be added) in a future major release.

(未来主要版本"可能会在Mockito 2中实现,其中可能会引入isA样式的类型检查.;请参阅

(The "future major release" may come true for Mockito 2, where isA-style type checks may be introduced. ; See commentary from Mockito committer Brice.)

泛型有助于为exchangethenReturn获取正确的参数,但是由于

The generics are helpful to get the right parameter for exchange and thenReturn, but because of type erasure none of that type information makes it into the CLASS file, let alone the JVM. The only Matcher that asserts the type of its argument is isA, which takes a class literal and won't help you for parameterized types.

您可以编写一个自定义的Matcher,以检查参数的类型和类型参数(如果它们不需要擦除),但是对于您的特定情况则没有必要.

You could write a custom Matcher that inspects an argument's type and type parameters, if they aren't subject to erasure, but for your specific case that's not necessary.

类型删除是 ParameterizedTypeReference 存在:它将通用信息捕获到一个子类中,在该子类中,不会删除参数化的类型 .相同的模式用于 TypeToken 在Guava或 Guice中的TypeLiteral .所有这些实现将参数化类型描述为实例.

Type erasure is the whole reason ParameterizedTypeReference exists: It captures the generics information into a subclass, where the parameterized type will not be erased. This same pattern is used for TypeToken in Guava or TypeLiteral in Guice. All of these implementations describe a parameterized type as an instance.

所有这些都很重要-包括

Importantly, all of them—including ParameterizedTypeReference—support equals and hashCode, so new ParameterizedTypeReference<A<B>>(){} equals new ParameterizedTypeReference<A<B>>(){} even though the instances are different. (See the code here.)

由于对相同参数化类型的引用相等,因此将Mockito的eq匹配器与其他引用一起使用,一切都会好起来的.

Because references to the same parameterized type are equal, use Mockito's eq matcher with a different reference, and things should be fine.

这篇关于将仿制药与Mockito匹配的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆