- Mockito 简介
Mockito是一个java仿冒架构,所谓的仿冒就是创建一个“虚拟”的java类来模拟一个java类的行为。之所以使用仿冒可能出于以下几个原因:
- 某个类已经进入单元测试,但是协作的类还没有开发完成;
- 协作类可能有缺陷,使用仿冒机制隔离缺陷;
- 模拟在单元测试阶段难以获得的对象,这些对象往往与环境和容器相关,如:HttpServletRequest
Mockito的三个事件,mock仿冒、验证(verification)和打桩(stubbing)。所谓的验证就是断言预期的行为,所谓的打桩就是mock对象在特定情况下的入参和返回
2. Maven 配置
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.11</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-test</artifactId>
<version>${spring.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.mockito</groupId>
<artifactId>mockito-all</artifactId>
<version>1.9.0</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.kubek2k</groupId>
<artifactId>springockito</artifactId>
<version>1.0.9</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.kubek2k</groupId>
<artifactId>springockito-annotations</artifactId>
<version>1.0.9</version>
<scope>test</scope>
</dependency>
3.使用
// 引用的静态资源
import static org.mockito.Mockito.*;
import static org.junit.Assert.*;
1.简单的例子演示验证和打桩
@Test
public void test(){
//制造一个mock 类
Map<String, Object> map = mock( Map.class );
map.put( "key", "value" );
map.clear();
//验证mock类是否调用
verify( map ).put( "key", "value" );// 只进行equals匹配
//验证clear至少调用过一次
verify( map, atLeast( 1 ) ).clear();
//打桩,尚未进行打桩的参数返回null
Assert.assertEquals( null, map.get( "any" ) );
// 进行打桩后
when( map.get( "Hello" ) ).thenReturn( "World" );
Assert.assertEquals( "World", map.get( "Hello" ) );
}
通过上面示例我们可以看出mock的没次调用我们都能进行监控,相应的mock可以准确的模拟对象的行为,忽略对象行为的实现细节。
mock未打桩时对象的返回值
- 返回Object的方法,mock默认返回null;
- 返回集合的方法,mock默认返回空;
- 返回数字的方法,mock默认返回0;
- 返回boolean的方法,mock默认返回false;
mock可以进行多次打桩,没次打桩都会覆盖前一个的值
参数匹配
@Test
public void test(){
List list = mock( List.class );
//任何整数参数
when( list.get( anyInt() ) ).thenReturn( null );
//两个任意参数
when( list.addAll(anyInt(), anyCollection() ) ).thenReturn( false );
}
mock除了支持任意整数和人与集合 还用 anyBoolean()、anyByte()、anyLong()等
参数捕获
@Test
public void test(){
List list = mock( List.class );
ArgumentCaptor<Integer> argument = ArgumentCaptor.forClass( Integer.class );
list.add( 1 );//这个参数会被捕获
verify( list ).add( argument.capture() ); //执行捕获
//后续对参数进行进一步验证
Assert.assertEquals( new Integer( 1 ), argument.getValue() );
}
返回值设定
@Test
public void test(){
List list = mock( List.class );
when( list.get( 0 ) ).thenReturn( 10 );
// 设置多个返回值,没次调用返回值不一样
when( list.get( 0 ) ).thenReturn( 1, 2, 3 );
//设置异常返回
when( list.get( 0 ) ).thenThrow( new RuntimeException() );
//依据入参决定返回值
when( list.get( anyInt() ) ).then( new Answer<Object>() {
public Object answer( InvocationOnMock invocation ) throws Throwable
{
return "El-" + invocation.getArguments()[0];
}
} );
//连续仿冒
when( list.get( 0 ) )
.thenReturn( 1 ) //第一次调用的返回值
.thenReturn( 2 )//第二次调用的返回值
.thenThrow( new RuntimeException() ); //以后调用的返回值
//设置未打桩方法的默认返回值
mock( List.class, new Answer<Object>() {
@Override
public Object answer( InvocationOnMock invocation ) throws Throwable
{
return null;
}
} );
}
验证调用次数
List list = mock( List.class );
//验证基于某个精确实参的调用发生的次数
verify( list, times( 1 ) ).add( 1 ); //一次
verify( list, times( 2 ) ).add( 2 ); //二次
verify( list, atLeastOnce() ).add( 1 ); //至少一次
verify( list, atLeast( 3 ) ).add( 3 ); //至少三次
verify( list, atMost( 3 ) ).add( 3 ); //至多三次
//参数匹配也适用于验证的时候:
verify( list, atMost( 3 ) ).add( argThat( new ArgumentMatcher<Object>() {
public boolean matches( Object argument )
{
return false;
}
} ) );
//断言Mock上没有发生任何未验证的调用
verifyNoMoreInteractions( list );
调用真是方法
List<Integer> list = new ArrayList<Integer>();
List<Integer> spy = spy( list );
//对真实对象进行打桩
when( spy.size() ).thenReturn( 100 );
//另外一种打桩方式,防止异常
doReturn( 1 ).when( spy ).get( 0 );
//下面这种方式是不行的,因为未打桩前会调用真实方法,导致IndexOutOfBoundsException
when( spy.get( 0 ) ).thenReturn( 1 );
spy.add( 1 );//调用真实的方法
spy.size();//调用仿冒的方法
verify( spy ).add( 1 ); //验证调用了一次
启动支持注解
//如果要启用注解支持,可以使用该运行类
//或者手工调用MockitoAnnotations.initMocks(this)
@RunWith ( MockitoJUnitRunner.class )
public class MockitoTest
{
//自动创建Mock
@Mock
private List<Object> list;
}
其他
List mock = mock(List.class);
when(mock.size()).thenReturn(10);
reset(mock); //重置仿冒
//单行调用即完成的Mock
Car boringStubbedCar = when(mock(Car.class).shiftGear()).thenThrow(EngineNotStarted.class).getMock();
分享到:
相关推荐
本资源包含的"Junit + Hamcrest + Mockito 单元测试 Jar包"是一个用于Java应用程序单元测试的工具集合,分别对应了三个流行的测试框架:JUnit、Hamcrest和Mockito。 JUnit是一个开源的Java单元测试框架,广泛应用于...
### Mockito 单元测试详解 #### 一、引言 在软件开发过程中,编写单元测试是一种常见的实践方式,用于确保代码质量与功能正确性。然而,在处理复杂的依赖关系时,传统的方法可能会遇到难题,比如当一个类依赖于多...
Mockito 是一个流行的 Java 测试框架,它使得单元测试更加容易,特别是当处理依赖于其他组件或服务的代码时。本篇文章将深入解析如何使用 Mockito 实现 Java 单元测试。 首先,让我们看一个简单的例子,有一个名为 ...
虽然测试分为单元测试,集成测试,系统测试等等,但是作为开发,我们可能不需要做这么多的测试(有时甚至不做……)接下来就说说和开发息息相关的单元测试以及集成测试。 单元测试就是模块测试,我的理解一个模块...
四、Mockito单元测试 Mockito是一个流行的Mocking框架,提供了mock对象的功能,可以用来模拟外部依赖项,例如数据库、Redis、外部服务等。 五、隔离外部依赖 在单元测试中,需要隔离外部依赖项,以避免外部依赖项...
springMVC 整合mockito单元测试学习-附件资源
Spring集成TestNG与Mockito框架单元测试方法的文档详细介绍了如何在Java Spring项目中,利用TestNG和Mockito框架进行单元测试。这种测试方法可以帮助开发者快速上手单元测试,并确保代码质量。文档涉及了多个方面,...
Mockito的重要入门资料Mockito 是单元测试中的一种常用技术,掌握Mockito对单元测试有重要影响
Mockito的重要入门资料Mockito 是单元测试中的一种常用技术,掌握Mockito对单元测试有重要影响1
下面是一个简单的Mockito单元测试示例,假设我们有一个`UserService`,它依赖于`UserRepository`: ```java import org.junit.jupiter.api.Test; import org.mockito.InjectMocks; import org.mockito.Mock; import...
TestNG和Mockito是两个在单元测试领域常用的工具,它们分别用于测试管理和模拟对象。本篇文章将深入探讨如何在Spring项目中集成TestNG和Mockito进行单元测试。 TestNG是一个强大的测试框架,它扩展了JUnit的功能,...
Mockito 和 JUnit 5 是两个非常流行的 Java 开发工具,它们一起提供了强大的单元测试支持。让我们深入探讨如何利用 Mockito 和 JUnit 5 搞定单元测试。 首先,JUnit 5 是一个广泛使用的 Java 测试框架,它提供了...
Mockito 是一个流行的 Java 单元测试框架,它允许开发者创建和配置模拟对象,以便在测试中隔离被测试代码。JUnit 是一个广泛使用的 Java 测试框架,它为编写和运行可重复的单元测试提供了基础。将 Mockito 和 JUnit ...
2. **Mockito**:在Android单元测试中,经常需要模拟(Mock)依赖项以隔离被测试的代码。Mockito是一个流行的Java库,允许我们创建和配置mock对象。例如,如果一个函数依赖于网络请求,我们可以用Mockito模拟网络...
基于Mockito和PowerMockito的Java单元测试指南 项目简介 本项目是一个专注于Java单元测试的指南,特别是使用Mockito和PowerMockito框架进行模拟测试。项目涵盖了从基础的Mockito使用到高级的PowerMockito功能,...
NewRelic静态Mockito单元测试springboot的样本测试,以及针对NewRelic的静态方法测试的PowerMockito。 编写了这个简单的示例测试用例,以找出在PowerMockito静态测试中为什么会出现随机错误的原因。 NewRelic....
Mockito 是一个流行的Java单元测试框架,用于模拟对象行为,使得测试更为简洁和可控。JUnit则是最常用的Java单元测试库,它提供了一种结构化的方式来编写和运行测试用例。当我们进行单元测试时,Mockito 和 JUnit ...
本话题主要关注Android单元测试,特别是结合了Volley网络库的测试实践,以及如何利用Mockito这样的模拟工具进行测试。 **Android单元测试** Android单元测试通常是指在没有实际设备或模拟器的情况下,对应用程序的...