如何为Map<String, SomeCustomClass>
创建参数捕获器?
我有遵循以下模式的代码:
import java.util.HashMap;
import java.util.Map;
public class CompoundClass {
public CompoundClass (String a, String b){
this.a = a;
this.b = b;
}
public String a;
public String b;
}
public class SubClass {
public void doSomeThingSubClass(Map<String, CompoundClass> mapSb) {
...
}
}
public class Example {
public SubClass sb;
public Example(SubClass sb) {
this.sb = sb;
}
public void doSomeThing () {
Map<String, CompoundClass> mapSb = new HashMap<>();
mapSb.put("x", new CompoundClass("aa","bb"));
sb.doSomeThingSubClass(mapSb);
}
}
我想测试是否调用了doSomethingSubClass(mapSb)
方法,从而我需要能够检查它被调用的参数。为此,我有以下单元测试:
@Test
void TestDoSomehing(){
SubClass sb = mock(SubClass.class);
Example ex = new Example(sb);
ArgumentCaptor<Map<String, CompoundClass>> argCaptor = ArgumentCaptor.forClass(Map<String, CompoundClass>.class);
ex.doSomeThing();
verify(sb).doSomeThingSubClass(argCaptor.capture());
System.out(argCaptor.getValue().get('x').a);
}
问题是上述 argCaptor 初始化会产生以下错误消息:"无法从参数化类型中进行选择"。因此,问题是如何以正确的方式声明初始化像 Map<String, SomeCustomeClass>
这样的映射对象的参数捕获器?提前感谢!
您可以执行以下操作之一:
带@SuppressWarnings("未选中"(
@Test
@SuppressWarnings("unchecked")
void TestDoSomething(){
SubClass sb = mock(SubClass.class);
Example ex = new Example(sb);
ArgumentCaptor<Map<String, CompoundClass>> argCaptor = ArgumentCaptor.forClass(Map.class);
ex.doSomeThing();
verify(sb).doSomeThingSubClass(argCaptor.capture());
System.out.println(argCaptor.getValue().get("x").a);
}
或使用 Junit5 和 @Captor 注释:
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.verify;
import java.util.HashMap;
import java.util.Map;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.TestInstance;
import org.junit.jupiter.api.TestInstance.Lifecycle;
import org.junit.jupiter.api.extension.ExtendWith;
import org.mockito.ArgumentCaptor;
import org.mockito.Captor;
import org.mockito.junit.jupiter.MockitoExtension;
@ExtendWith(MockitoExtension.class)
@TestInstance(Lifecycle.PER_METHOD)
public class TestDoSomething {
@Captor
private ArgumentCaptor<Map<String, CompoundClass>> argCaptor;
@Test
void TestDoSomething2(){
SubClass sb = mock(SubClass.class);
Example ex = new Example(sb);
ex.doSomeThing();
verify(sb).doSomeThingSubClass(argCaptor.capture());
System.out.println(argCaptor.getValue().get("x").a);
}
}
您可以使用 Mockito 的 Captor
注释来声明 ArgumentCaptor
的参数化实例。
例如,以下测试编译并输出aa
:
@Captor
private ArgumentCaptor<Map<String, CompoundClass>> argCaptor;
@Test
void TestDoSomehing(){
MockitoAnnotations.initMocks(this);
SubClass sb = mock(SubClass.class);
Example ex = new Example(sb);
ex.doSomeThing();
verify(sb).doSomeThingSubClass(argCaptor.capture());
System.out.println(argCaptor.getValue().get("x").a);
}
来自Javadocs:
使用
@Captor
批注的优点之一是可以避免与捕获复杂泛型类型相关的警告。