Mockito 小结
Mockito 小结
为什么要使用Mock
进行测试
传统测试,后端工程师依赖一些第三方的接口(支付、定时任务等不方便真实测试的接口),前端工程师依赖后端的接口,测试工程师依赖前端的接口
使用
Mock
,使用虚拟对象进行测试,达到解耦、并行开发。
常见的mock
框架
Mockito
的常用API
添加
Mockito
依赖 和Junit
依赖
<dependency> <groupId>org.mockito</groupId> <artifactId>mockito-core</artifactId> <version>3.8.0</version> <scope>test</scope> </dependency> <dependency> <groupId>junit</groupId> <artifactId>junit</artifactId> <version>4.12</version> <scope>test</scope> </dependency>
生成 mock(模拟)对象 (多种方式)
若无特殊说明,所有的地方均静态导入了这个包
import static org.mockito.Mockito.*;
直接创建mock对象
//create mockList mockedList = mock(List.class);
通过注解注入mock对象
@RunWith(MockitoJUnitRunner.class)public class Test { @Mock private AService aService; @Test public void test() { //handle aService } interface AService { public boolean test(); } @Service class AServiceImpl implements AService { @Override public boolean test() { return false; } } }
拓展,创建spy对象
List mockList= mock(List.class); List spy = spy(mockList);
使用mock对象
测试桩(Stub)模式:默认情况,一个mock对象的函数返回为null或基础类型的默认值。测试桩函数会覆盖函数返回值。
一个简单的例子
// 创建 mock 对象 List mockedList = mock(List.class); // 测试桩 when(mockedList.get(0)).thenReturn("first"); // 连续测试桩 when(mockedList.get(1)).thenReturn("once").thenReturn("twice"); // 异常测试桩 when(mockedList.get(2)).thenThrow(new RuntimeException()); // 打印 first System.out.println(mockedList.get(0)); // 打印 once System.out.println(mockedList.get(1)); // 打印 twice System.out.println(mockedList.get(1)); // 打印 null System.out.println(mockedList.get(999)); // 报 RuntimeException 异常 System.out.println(mockedList.get(2));
使用 anyXXX()
// 创建 mock 对象 List mockedList = mock(List.class); when(mockedList.get(anyInt())).thenReturn("element"); //打印 element System.out.println(mockedList.get(999)); verify(mockedList).get(anyInt());
次数验证
// 创建 mock 对象 List mockedList = mock(List.class); mockedList.add("once"); mockedList.add("twice"); mockedList.add("twice"); mockedList.add("three times"); mockedList.add("three times"); mockedList.add("three times"); // 1次 once verify(mockedList, times(1)).add("once"); // 2次 twice verify(mockedList, times(2)).add("twice"); // 3次 three times verify(mockedList, times(3)).add("three times"); // 一次都不存在 never happened verify(mockedList, never()).add("never happened"); // 拓展 // 最少一次 three times verify(mockedList, atLeastOnce()).add("three times"); // 最少两次 five times// verify(mockedList, atLeast(2)).add("five times"); // 最多5次 three times// verify(mockedList, atMost(5)).add("three times");
顺序验证
// 创建 mock 对象, 进行单个对象的顺序验证 List singleMock = mock(List.class); singleMock.add("was added first"); singleMock.add("was added second"); InOrder inOrder = inOrder(singleMock); inOrder.verify(singleMock).add("was added first"); inOrder.verify(singleMock).add("was added second"); // 创建多个 mock 对象,进行多个mock对象的顺序验证 List firstList = mock(List.class); List secondList = mock(List.class); firstList.add("was added first"); secondList.add("was added second"); InOrder order = inOrder(firstList, secondList); order.verify(firstList).add("was added first"); order.verify(secondList).add("was added second");