单元测试入坑初探(6)

先填坑发布上期的工具包

链接: https://pan.baidu.com/s/1isf52fPy9htlq-n7oLdyZA密码: h2yu

开门见山直接来

Jmockit

Jmockit功能和PowerMock类似,某些功能甚至更为强大,但个人感觉其代码的可读性并不强。

Jmockit也可以分类为非局部模拟与局部模拟,区分在于Expectations块是否有参数,有参数的是局部模拟,反之是非局部模拟。而Expectations块一般由Expectations类和NonStrictExpectations类定义。用Expectations类定义的,则mock对象在运行时只能按照 Expectations块中定义的顺序依次调用方法,不能多调用也不能少调用,所以可以省略掉Verifications块;而用NonStrictExpectations类定义的,则没有这些限制,所以如果需要验证,则要添加Verifications块。

现在举例说明Jmockit的用法:

例4.1 非局部模拟Expectations类定义

@Mocked//用@Mocked标注的对象,不需要赋值,jmockit自动mockClass1Mocked obj;

@Test

publicvoidtestMockNormalMethod1() {

newExpectations() {

{

obj.hello("z3");

returns("hello l4", "hello w5");

obj.hello("张三");

result="hello李四";

}

};

assertEquals("hello l4", obj.hello("z3"));

assertEquals("hello w5", obj.hello("z3"));

assertEquals("hello李四", obj.hello("张三"));

try{

obj.hello("z3");

}catch(Throwable e) {

}

try{

obj.show();

}catch(Throwable e) {

}

}

例4.2 非局部模拟 NonStrictExpectations类定义

publicvoidtestMockNormalMethod2() {

newNonStrictExpectations() {

{

obj.hello("z3");

returns("hello l4", "hello w5");

}

};

assertEquals("hello l4", obj.hello("z3"));

assertEquals("hello w5", obj.hello("z3"));

assertEquals("hello w5", obj.hello("z3"));//会返回在NonStrictExpectations块中定义的最后一个返回值obj.show();

newVerifications() {

{

obj.hello("z3");

times = 3;

obj.show();

times = 1;

}

};

}

运行这个测试会发现show()方法没有在控制台输出打印语句,说明是Jmockit对show方法也进行了默认mock。

例4.3 局部模拟

@Test

publicvoidtestMockNormalMethod()throwsIOException {

finalClass1Mocked obj =newClass1Mocked();//也可以不用@Mocked标注,但需要final关键字

newNonStrictExpectations(obj) {

{

obj.hello("z3");

result = "hello l4";

}

};

assertEquals("hello l4", obj.hello("z3"));

assertEquals("hello张三", obj.hello("张三"));

newVerifications() {

{

obj.hello("z3");

times = 1;

obj.hello("张三");

times = 1;

}

};

}

运行这个测试发现hello("z3")返回由Expectations块定义的值,但hello("张三")执行的是实际的代码。

例4.4 模拟静态方法

@Test

publicvoidtestMockStaticMethod() {

newNonStrictExpectations(Class2Mocked.class) {

{

Class2Mocked.getDouble(1);

result = 3;

}

};

assertEquals(3, Class2Mocked.getDouble(1));

newVerifications() {

{

Class2Mocked.getDouble(1);

times = 1;

}

};

}

例4.5 模拟私有方法

@Test

publicvoidtestMockPrivateMethod()throwsException {

finalClass2Mocked obj =newClass2Mocked();

newNonStrictExpectations(obj) {

{

this.invoke(obj, "multiply3", 1);

result = 4;

}

};

String actual = obj.getTripleString(1);

assertEquals("4", actual);

newVerifications() {

{

this.invoke(obj, "multiply3", 1);

times = 1;

}

};

}

例4.6 设置私有属性的值

假设有一个类需要被模拟的类如下:

publicclassClass3Mocked {

privateString name = "name_init";

publicString getName() {

returnname;

}

privatestaticString className="Class3Mocked_init";

publicstaticString getClassName(){

returnclassName;

}

publicstaticintgetDouble(inti){

returni*2;

}

publicintgetTriple(inti){

returni*3;

}

}

如下可以设置私有属性的值:

@Test

publicvoidtestMockPrivateProperty()throwsIOException {

finalClass3Mocked obj =newClass3Mocked();

newNonStrictExpectations(obj) {

{

this.setField(obj, "name", "name has bean change!");

}

};

assertEquals("name has bean change!", obj.getName());

}

例4.7 设置静态私有属性的值

@Test

publicvoidtestMockPrivateStaticProperty()throwsIOException {

newNonStrictExpectations(Class3Mocked.class) {

{

this.setField(Class3Mocked.class, "className", "className has bean change!");

}

};

assertEquals("className has bean change!", Class3Mocked.getClassName());

}

例4.8 改写普通方法的内容

@Test

publicvoidtestMockNormalMethodContent()throwsIOException {

finalClass3Mocked obj =newClass3Mocked();

newNonStrictExpectations(obj) {

{

newMockUp() {

@Mock

publicintgetTriple(inti) {

returni * 30;

}

};

}

};

assertEquals(30, obj.getTriple(1));

assertEquals(60, obj.getTriple(2));

}

例4.9 改写静态方法的内容

如果要改写Class3Mocked类的静态getDouble方法,则需要新建一个类含有与getDouble方法相同的函数声明,并且用@Mock标注,如下:

publicclassClass4Mocked {

@Mock

publicstaticintgetDouble(inti){

returni*20;

}

}

如下即可改写:

@Test

publicvoidtestDynamicMockStaticMethodContent()throwsIOException {

Mockit.setUpMock(Class3Mocked.class, Class4Mocked.class);

assertEquals(20, Class3Mocked.getDouble(1));

assertEquals(40, Class3Mocked.getDouble(2));

}

from:http://www.cnblogs.com/huangbin/archive/2013/04/27/3047671.html

这回不墨迹直接发这系列也没下期了到哪看

直接来

链接: https://pan.baidu.com/s/13-ECOUOj5ajyiWyA0XiJHw密码: vhrs

  • 发表于:
  • 原文链接https://kuaibao.qq.com/s/20180619G0N04A00?refer=cp_1026
  • 腾讯「云+社区」是腾讯内容开放平台帐号(企鹅号)传播渠道之一,根据《腾讯内容开放平台服务协议》转载发布内容。
  • 如有侵权,请联系 yunjia_community@tencent.com 删除。

扫码关注云+社区

领取腾讯云代金券