java 中showinfo方法,jmockito模拟方法中参数如何指定

在做单元测试的时候,经常会遇到mock类的方法的情景。在写单测过程中,遇到一些问题,比较困惑,便做了一些测试,并得出一个结论:

在mock类的方法时,当符合 (mock参数).equals(实际调用过程中的参数)时,才可以mock成功;当参数为基本类型时,可以使用angLong等。

下面是测试的欢乐时间啦:

首先看测试基础类:

public class Person {

private String name;

private Integer age;

private Person friend;

}

public class PersonService {

public void showFriendInfo(Person person){

System.out.println("show friend info ...");

showInfo1(new Person("shoren", 22));

showInfo2(person.getFriend());

}

public void showInfo1(Person person){

System.out.println("show info1 ...");

}

public void showInfo2(Person person){

System.out.println("show info2 ...");

}

public void showPersonInfo(Person person){

System.out.println("show person info ...");

showName("shoren");

showName2(person.getName());

}

public void showName(String name){

System.out.println("show name1 : " + name);

}

public void showName2(String name){

System.out.println("show name2 : " + name);

}

}

先看参数为基本类型时:

1. 参数为基本类型时,使用any都可以成功mock。

@Test

public void testShowPersonInfoUsingAny(){

final Person person = new Person("manyao", 23);

new NonStrictExpectations(personService){{

Deencapsulation.invoke(personService, "showName", anyString);

Deencapsulation.invoke(personService, "showName2", anyString);

}};

personService.showPersonInfo(person);

}

结果为

show person info ...

2. 参数为基本类型,mock时传入真实的值,且与之前值相等,可以mock成功。

@Test

public void testShowPersonInfoUsingData(){

final Person person = new Person("manyao", 23);

new NonStrictExpectations(personService){{

Deencapsulation.invoke(personService, "showName", new String("shoren"));

Deencapsulation.invoke(personService, "showName2", new String("manyao"));

}};

personService.showPersonInfo(person);

}

结果为:

show person info ...

3. 参数为基本类型,mock时传入真实的值,若实际调用值与之不相等,则mock失败。

@Test

public void testShowPersonInfoUsingData2(){

final Person person = new Person("manyao", 23);

new NonStrictExpectations(personService){{

Deencapsulation.invoke(personService, "showName", new String("tata"));

Deencapsulation.invoke(personService, "showName2", person.getName());

}};

personService.showPersonInfo(person);

}

结果为

show person info ...

show name1 : shoren

得出结论:如果参数为基本类型,则mock参数为anyXXX 或者 与实际调用的参数值相等时,可以mkco成功。

再来看参数为复杂类型:

4. 参数为复杂参数时,使用any做类型转换,mock失败。

@Test

public void testShowFriendUseAny(){

final Person person = new Person("manyao", 23);

person.setFriend(new Person("friend", 24));

new NonStrictExpectations(personService){{

Deencapsulation.invoke(personService, "showInfo1", (Person)any);

Deencapsulation.invoke(personService, "showInfo2", (Person)any);

}};

personService.showFriendInfo(person);

}

结果为

java.lang.IllegalArgumentException: Invalid null value passed as argument 0

at jmockito.PersonServiceTest$4.(PersonServiceTest.java:92)

at jmockito.PersonServiceTest.testShowFriendUseAny(PersonServiceTest.java:91)

at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)

at com.intellij.junit4.JUnit4IdeaTestRunner.startRunnerWithArgs(JUnit4IdeaTestRunner.java:78)

at com.intellij.rt.execution.junit.JUnitStarter.prepareStreamsAndStart(JUnitStarter.java:212)

at com.intellij.rt.execution.junit.JUnitStarter.main(JUnitStarter.java:68)

at com.intellij.rt.execution.application.AppMain.main(AppMain.java:140)

5. 参数为复杂参数,mock参数为具体值时,mock参数 equals 实际调用值时,mock成功。

@Test

public void testShowFriendUseData(){

final Person person = new Person("manyao", 23);

person.setFriend(new Person("friend", 24));

new NonStrictExpectations(personService){{

Deencapsulation.invoke(personService, "showInfo1", new Person("shoren", 22));

Deencapsulation.invoke(personService, "showInfo2", person.getFriend());

}};

personService.showFriendInfo(person);

}

结果为

show friend info ...

show info1 ...

到这里,似乎可以得出这样一个结论,mock内部调用方法时,其mock参数与外部参数的关系,应该与实际执行时,参数的关系一致。即实际调用中,showInfo2的参数是person.getFriend(),

所以,在mock方法showInfo2时,其参数也应该是person.getFriend()。

如果是这样的话,mock方法showInfo1时,又该如何呢?在Person中添加equals方法测试一下。

6. 参数为复杂参数时,(mock参数).equals(实际参数)时,mock成功。

@Test

public void testShowFriendUseData1(){

final Person person = new Person("manyao", 23);

person.setFriend(new Person("friend", 24));

new NonStrictExpectations(personService){{

Deencapsulation.invoke(personService, "showInfo1", new Person("shoren", 22));

Deencapsulation.invoke(personService, "showInfo2", new Person("friend", 24));

}};

personService.showFriendInfo(person);

}

结果为

show friend info ...

7. 参数为复杂参数时,修改equals方法,总是return true时。不论mock参数如何,mock成功.

@Test

public void testShowFriendUseData2(){

final Person person = new Person("manyao", 23);

person.setFriend(new Person("friend", 24));

new NonStrictExpectations(personService){{

Deencapsulation.invoke(personService, "showInfo1", new Person());

Deencapsulation.invoke(personService, "showInfo2", new Person());

}};

personService.showFriendInfo(person);

}

结果为

show friend info ...

综上,我们得出结论:

在mock类的方法时,当符合 (mock参数).equals(实际调用过程中的参数)时,才可以mock成功;当参数为基本类型时,可以使用angLong等。

当然,像这一类的问题,如果要了解清楚,最好还是去阅读源代码。暂时没有时间做这件事。

C#方法中参数ref和out的解析

一.C#方法中参数类型 有4种参数类型,有时候很难记住它们的不同特征,下图对它们做一个总结,使之更容易比较和对照. 二.C#方法中的参数 1.值参数 使用值参数,通过复制实参的值到形参的方式把数据传递 ...

详解SpringMVC中Controller的方法中参数的工作原理[附带源码分析]

目录 前言 现象 源码分析 HandlerMethodArgumentResolver与HandlerMethodReturnValueHandler接口介绍 HandlerMethodArgumen ...

详解SpringMVC中Controller的方法中参数的工作原理

Spring MVC中Controller的处理方法的参数可以是Integer,String,自定义对象,ServletRequest,ServletResponse,ModelAndView等等,非 ...

详解SpringMVC中Controller的方法中参数的工作原理——基于maven

转自:http://www.tuicool.com/articles/F7byQn 前言 SpringMVC是目前主流的Web MVC框架之一. 如果有同学对它不熟悉,那么请参考它的入门blog:ht ...

【MVC - 参数原理】详解SpringMVC中Controller的方法中参数的工作原理[附带源码分析]

前言 SpringMVC是目前主流的Web MVC框架之一. 如果有同学对它不熟悉,那么请参考它的入门blog:http://www.cnblogs.com/fangjian0423/p/spring ...

动作方法中 参数,Json

一.方法中可以出现的参数类 1.HttpServletRequest 2.HttpServletResponse 3.HttpSession 4.Model 二.返回接收json数据 1. 接收,返回 ...

main方法中参数"String[ ] args"详解

1.在编写完一个有主方法的java文件时,需要在cmd窗口中先编译此java文件(javac xxx.java),然后再运行(java xxx) 其实在运行java xxx的时候如果后面跟着参数用空格 ...

JAVA方法中参数到底是值传递还是引用传递

当一个对象被当作参数传递到一个方法后,在此方法内可以改变这个对象的属性,那么这里到底是值传递还是引用传递? 答:是值传递.Java 语言的参数传递只有值传递.当一个实例对象作为参数被传递到方法中时,参 ...

TCanvas.CopyRect方法中参数CopyMode的意义

首先看可能取值: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 cmBlackness = BLACKNESS; cmDstInvert = DSTINVERT; cmMer ...

随机推荐

Java 导入Excel文件到数据库

原文:http://www.jb51.net/article/44021.htm 项目中要求读取excel文件内容,并将其转化为xml格式.常见读取excel文档一般使用POI和JExcelAPI这两 ...

gym923B

Even though he isn't a student of computer science, Por Costel the pig has started to study Graph Th ...

网页闯关游戏(riddle webgame)--游戏玩法和整体介绍

前言: 记得上大学那会, 有位传说中的大牛, 写了一个网页闯关类的游戏. 当时我们玩得不亦乐乎, 也是第一次接触到这种形式的游戏. 不过当时纯玩家心态, 并没有想过去创造一个. 最近想起这事, 突然想 ...

MyCat 学习笔记 第七篇.数据分片 之 按数据范围分片

1 应用场景 Mycat 其实自带了2个数据范围分片的方案,一个是纯数据范围的分片,比如 1至 10000 号的数据放到分片1 ,10001 至 20000号数据放到分片2里. 另一个是数据常量形式的 ...

Linux+postfix+extmail+dovecot打造基于web页面的邮件系统

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值