Java 使用 Mockito 的通用“any()”方法

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/1778744/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-12 22:32:37  来源:igfitidea点击:

Using Mockito's generic "any()" method

javaunit-testingmockingmockito

提问by ripper234

I have an interface with a method that expects an array of Foo:

我有一个接口,它的方法需要一个数组Foo

public interface IBar {
  void doStuff(Foo[] arr);
}

I am mocking this interface using Mockito, and I'd like to assert that doStuff()is called, but I don't want to validate what argument are passed - "don't care".

我正在使用 Mockito 嘲笑这个接口,我想断言它doStuff()被调用,但我不想验证传递了什么参数 - “不关心”。

How do I write the following code using any(), the generic method, instead of anyObject()?

如何使用any()泛型方法而不是编写以下代码anyObject()

IBar bar = mock(IBar.class);
...
verify(bar).doStuff((Foo[]) anyObject());

采纳答案by Lii

Since Java 8 you can use the argument-less anymethod and the type argument will get inferred by the compiler:

从 Java 8 开始,您可以使用无参数any方法,编译器会推断类型参数:

verify(bar).doStuff(any());


Explanation

解释

The new thing in Java 8 is that the target typeof an expression will be used to infer type parameters of its sub-expressions. Before Java 8 only arguments to methods where used for type parameter inference (most of the time).

Java 8 中的新事物是表达式的目标类型将用于推断其子表达式的类型参数。在 Java 8 之前,只有方法的参数用于类型参数推断(大部分时间)。

In this case the parameter type of doStuffwill be the target type for any(), and the return value type of any()will get chosen to match that argument type.

在这种情况下, 的参数类型doStuff将是 的目标类型any(),并且 的返回值类型any()将被选择以匹配该参数类型。

This mechanism was added in Java 8 mainly to be able to compile lambda expressions, but it improves type inferences generally.

Java 8 中添加了这种机制主要是为了能够编译 lambda 表达式,但它总体上改进了类型推断。



Primitive types

原始类型

This doesn't work with primitive types, unfortunately:

不幸的是,这不适用于原始类型:

public interface IBar {
    void doPrimitiveStuff(int i);
}

verify(bar).doPrimitiveStuff(any()); // Compiles but throws NullPointerException
verify(bar).doPrimitiveStuff(anyInt()); // This is what you have to do instead

The problem is that the compiler will infer Integeras the return value of any(). Mockito will not be aware of this (due to type erasure) and return the default value for reference types, which is null. The runtime will try to unbox the return value by calling the intValuemethod on it before passing it to doStuff, and the exception gets thrown.

问题是编译器会推断Integerany(). Mockito 不会意识到这一点(由于类型擦除)并返回引用类型的默认值,即null. 运行时将尝试通过在将返回值intValue传递给 之前调用其上的方法来取消装箱返回值doStuff,并抛出异常。

回答by jitter

This should work

这应该工作

import static org.mockito.ArgumentMatchers.any;
import static org.mockito.Mockito.verify;

verify(bar).DoStuff(any(Foo[].class));

回答by thilko

You can use Mockito.isA()for that:

你可以使用Mockito.isA()

import static org.mockito.Matchers.isA;
import static org.mockito.Mockito.verify;

verify(bar).doStuff(isA(Foo[].class));

http://site.mockito.org/mockito/docs/current/org/mockito/Matchers.html#isA(java.lang.Class)

http://site.mockito.org/mockito/docs/current/org/mockito/Matchers.html#isA(java.lang.Class)

回答by Maciej Kowalski

As I needed to use this feature for my latest project (at one point we updated from 1.10.19), just to keep the users (that are already using the mockito-core version 2.1.0 or greater) up to date, the static methods from the above answers should be taken from ArgumentMatchersclass:

因为我需要在我的最新项目中使用这个功能(有一次我们从 1.10.19 更新),只是为了让用户(已经在使用2.1.0 或更高版本mockito-core 版本)保持最新,静态上述答案中的方法应取自ArgumentMatchers课堂:

import static org.mockito.ArgumentMatchers.isA;
import static org.mockito.ArgumentMatchers.any;

Please keep this in mind if you are planning to keep your Mockito artefacts up to date as possibly starting from version 3, this class may no longer exist:

如果您打算从版本 3 开始更新您的 Mockito 人工制品,请记住这一点,此类可能不再存在:

As per 2.1.0 and above, Javadoc of org.mockito.Matchers states:

根据 2.1.0 及更高版本,org.mockito.Matchers 的 Javadoc 声明:

Use org.mockito.ArgumentMatchers. This class is now deprecated in order to avoid a name clash with Hamcrest * org.hamcrest.Matchersclass. This class will likely be removed in version 3.0.

使用org.mockito.ArgumentMatchers. 这个类现在已被弃用,以避免与 Hamcrest *org.hamcrest.Matchers类发生名称冲突。此类可能会在 3.0 版中删除。

I have written a little article on mockito wildcardsif you're up for further reading.

如果您愿意进一步阅读,我已经写了一篇关于mockito 通配符的小文章。