Mockito.any () проходить интерфейс с универсальными

171

Можно ли передать тип интерфейса с генериками?

Интерфейс:

public interface AsyncCallback<T>

В моем методе испытаний:

Mockito.any(AsyncCallback.class)

Укладка <ResponseX>сзади или .classне работает.

lrxw
источник

Ответы:

306

Существует безопасный для типов способ: используйте ArgumentMatchers.any()и уточняйте его с помощью типа:

ArgumentMatchers.<AsyncCallback<ResponseX>>any()
thSoft
источник
4
Я подтверждаю, что этот ответ работает и правильно подавляет предупреждение.
Кевинарпе
1
Это не совсем безопасно, поскольку реальный метод в любом случае может быть вызван только с правильно введенным аргументом. Нужно было просто удовлетворить компилятор pre-java8, в котором отсутствовал такой тип вывода.
herman
Я использовал что-то вроде этого ResponseEntity <List <Map <String, Object >>> responseEntity = Matchers. <ResponseEntity <List <Map <String, Object >>>> any (); И это всегда возвращает нуль
Арун
6
С новыми версиями Mockito:(Matchers.<AsyncCallback<ResponseX>>any()
Pierrefevrier
15
Matchersна самом деле устарела, но ArgumentMatchersработает.
Guijob
67

Используя Java 8, вы можете просто использовать any()(при условии статического импорта) без аргумента или параметра типа из-за расширенного вывода типа. Компилятор теперь знает из целевого типа (тип аргумента метода), что вы на самом деле имеете в виду Matchers.<AsyncCallback<ResponseX>>any(), что является решением до Java 8.

Герман
источник
Также не any()подходит AsyncCallback<AnyOtherType>?
Мэтью Прочитал
@MatthewRead Using AsyncCallback<AnyOtherType>не должен даже компилироваться, если тип аргумента - «AsyncCallback <ResponseX>».
Герман
1
Меня интересует ситуация, когда тип аргумента также является универсальным, но вы хотите смоделировать его только для одного конкретного типа (или смоделировать его для нескольких типов по-разному). Учитывая , when(x.y(any())).thenAnswer(...)например, где yнаходится public <T> T y(AsyncCallback<T> arg). Возможно, было бы лучше проверить тип в ответе, если это то, что нужно?
Мэтью Прочитал
2
@MatthewRead Из-за стирания фактический тип не может быть проверен во время выполнения Mockito. Так что вы даже не можете использовать isA(). Если объект содержит Classобъект, соответствующий типу, и интерфейс предоставляет это, я думаю, вы можете проверить это в пользовательском сопоставителе. Или, например, в случае Collectionвы можете проверить тип элементов.
Герман
1
Matchersбыл заменен на ArgumentMatchersMockito v2
bheussler
15

Я должен был принять следующий механизм, чтобы учесть дженерики:

import static org.mockito.Matchers.any;
List<String> list = any();
when(callMyMethod.getResult(list)).thenReturn(myResultString);

Надеюсь, это кому-нибудь поможет.

theINtoy
источник
3
Смотрите мой ответ: это больше не нужно с Java 8.
herman
5

Публикация комментария Pierrefevrier в качестве ответа, который может быть полезен, если он присутствует в ответе вместо комментариев.

С новыми версиями Mockito: (Matchers.<AsyncCallback<ResponseX>>any()

провисать
источник
1
я добавил его комментарий к первоначальному ответу
Joergi
2

В дополнение к ответу thSoft размещение квалифицированного вызова метода any () означало, что я могу удалить квалификацию, поскольку возвращаемый тип допускает логический вывод:

private HashMap<String, String> anyStringStringHashMap() {
    return Matchers.any();
}
JWGS
источник
0

Вы можете просто разыграть его, добавив подавляющие предупреждения, если хотите:

@SuppressWarnings("unchecked")    
AsyncCallback<ResponseX> callback = Mockito.any(AsyncCallback.class)

Если бы Java допускала «универсальные» генерики, они могли бы иметь такой метод, который вы ищете

private static <T, E> T<E> mock(Class<T<E>> clazz)
Гарретт Холл
источник
Когда я попробовал это, я получил ошибку в своем тесте:You cannot use argument matchers outside of verification or stubbing.
kevinarpe
Не очень хорошая идея @SuppressWarnings: pre-java 8, если вы собираетесь назначить ее отдельной переменной, вы можете просто использовать ее, any()как в ответе Интой. Теперь с Java 8, any()могут быть использованы inline без необходимости отдельного назначения.
herman
@kevinarpe, если у вас есть несколько сопоставлений аргументов, они должны вызываться по порядку, как указано в языке Java.
TWiStErRob
0

У меня была похожая проблема с использованием Spring Example:

Mockito.when(repo.findAll(Mockito.<Example<SrvReqToSupplierComment>>any()))
            .thenReturn(Lists.emptyList());

Здесь вы должны использовать квалификацию, так как метод findAll может иметь несколько типов, например Sortи Iterable. Вы также можете использовать Mockito.any(Example.class)с предупреждением безопасности типа.

gagarwa
источник