Java Mockito 的 argumentCaptor 示例
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/36253040/
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
Example of Mockito's argumentCaptor
提问by Ujjwal
Can anyone please provide me an example showing how to use the org.mockito.ArgumentCaptor
class and how it is different from simple matchersthat are provided with mockito.
任何人都可以给我提供一个示例,展示如何使用org.mockito.ArgumentCaptor
该类以及它与 mockito 提供的简单匹配器有何不同。
I read the provided mockito documents but those doesn't illustrate it clearly, none of them are able to explain it with clarity.
我阅读了提供的 mockito 文档,但这些文档并没有清楚地说明它,他们都无法清楚地解释它。
回答by fge
The two main differences are:
两个主要区别是:
- when you capture even a single argument, you are able to make much more elaborate tests on this argument, and with more obvious code;
- an
ArgumentCaptor
can capture morethan once.
- 当您捕获甚至一个参数时,您就能够对这个参数进行更精细的测试,并使用更明显的代码;
- 一个
ArgumentCaptor
可以捕捉更比一次。
To illustrate the latter, say you have:
为了说明后者,假设您有:
final ArgumentCaptor<Foo> captor = ArgumentCaptor.forClass(Foo.class);
verify(x, times(4)).someMethod(captor.capture()); // for instance
Then the captor will be able to give you access to all 4 arguments, which you can then perform assertions on separately.
然后捕获者将能够让您访问所有 4 个参数,然后您可以分别对其执行断言。
This or any number of arguments in fact, since a VerificationMode
is not limited to a fixed number of invocations; in any event, the captor will give you access to all of them, if you wish.
事实上,这个或任何数量的参数,因为 aVerificationMode
不限于固定数量的调用;无论如何,如果您愿意,俘虏者将允许您访问所有这些文件。
This also has the benefit that such tests are (imho) much easier to write than having to implement your own ArgumentMatcher
s -- particularly if you combine mockito with assertj.
这也有一个好处,即此类测试(恕我直言)比必须实现自己的ArgumentMatcher
s更容易编写- 特别是如果您将 mockito 与 assertj 结合使用。
Oh, and please consider using TestNG instead of JUnit.
哦,请考虑使用 TestNG 而不是 JUnit。
回答by Slava Shpitalny
I agree with what @fge said, more over. Lets look at example. Consider you have a method:
我同意@fge 所说的,更多。让我们看看例子。考虑你有一个方法:
class A {
public void foo(OtherClass other) {
SomeData data = new SomeData("Some inner data");
other.doSomething(data);
}
}
Now if you want to check the inner data you can use the captor:
现在如果你想检查内部数据,你可以使用捕获器:
// Create a mock of the OtherClass
OtherClass other = mock(OtherClass.class);
// Run the foo method with the mock
new A().foo(other);
// Capture the argument of the doSomething function
ArgumentCaptor<SomeData> captor = ArgumentCaptor.forClass(SomeData.class);
verify(other, times(1)).doSomething(captor.capture());
// Assert the argument
SomeData actual = captor.getValue();
assertEquals("Some inner data", actual.innerData);
回答by Lho Ben
The steps in order to make a full check are:
进行全面检查的步骤是:
Prepare the captor :
准备俘虏:
ArgumentCaptor<SomeArgumentClass> someArgumentCaptor = ArgumentCaptor.forClass(SomeArgumentClass.class);
verify the call to dependent on component (collaborator of subject under test) times(1), is the default value, so ne need to add it.
验证对依赖组件(被测对象的合作者)times(1) 的调用是默认值,所以需要添加它。
verify(dependentOnComponent, times(1)).send(someArgumentCaptor.capture());
Get the argument passed to collaborator
获取传递给合作者的参数
SomeArgumentClass someArgument = messageCaptor.getValue();
someArgument can be used for assertions
someArgument 可用于断言
回答by Vikram singh
Here I am giving you a proper example of one callback method . so suppose we have a method like method login() :
在这里,我给你一个回调方法的正确例子。所以假设我们有一个类似方法 login() 的方法:
public void login() {
loginService = new LoginService();
loginService.login(loginProvider, new LoginListener() {
@Override
public void onLoginSuccess() {
loginService.getresult(true);
}
@Override
public void onLoginFaliure() {
loginService.getresult(false);
}
});
System.out.print("@@##### get called");
}
I also put all the helper class here to make the example more clear: loginService class
为了让例子更清晰,我也把所有的帮助类放在这里: loginService 类
public class LoginService implements Login.getresult{
public void login(LoginProvider loginProvider,LoginListener callback){
String username = loginProvider.getUsername();
String pwd = loginProvider.getPassword();
if(username != null && pwd != null){
callback.onLoginSuccess();
}else{
callback.onLoginFaliure();
}
}
@Override
public void getresult(boolean value) {
System.out.print("login success"+value);
}}
and we have listener LoginListener as :
我们有监听器 LoginListener 为:
interface LoginListener {
void onLoginSuccess();
void onLoginFaliure();
}
}
now I just wanted to test the method login() of class Login
现在我只想测试类 Login 的方法 login()
@Test
public void loginTest() throws Exception {
LoginService service = mock(LoginService.class);
LoginProvider provider = mock(LoginProvider.class);
whenNew(LoginProvider.class).withNoArguments().thenReturn(provider);
whenNew(LoginService.class).withNoArguments().thenReturn(service);
when(provider.getPassword()).thenReturn("pwd");
when(provider.getUsername()).thenReturn("username");
login.getLoginDetail("username","password");
verify(provider).setPassword("password");
verify(provider).setUsername("username");
verify(service).login(eq(provider),captor.capture());
LoginListener listener = captor.getValue();
listener.onLoginSuccess();
verify(service).getresult(true);
also dont forget to add annotation above the test class as
也不要忘记在测试类上方添加注释
@RunWith(PowerMockRunner.class)
@PrepareForTest(Login.class)