当使用Moq来Mock一个具体的类,类里的方法为virtual时,Moq会将当前类,所有的virtual方法默认重写成空实现。

如果我们想要访问真实的代码,有两种方法

1、在创建Mock时,设置CallBack为True:则当前类里所有的方法全访问真实代码

var mock = new Mock<ChildClass>() { CallBase = true};
mock.Object.ChildDo();

2、只想单个访问真实代码,可以Setup此方法后,调用.CallBase()方法

mock.Setup(a => a.ChildDo()).CallBase();

-------------------------------------

当我们要监控父类里的虚方法时,这里有一个很恶心的地方:

如果子类里使用base.BaseDo()来调用父类的功能,父类的BaseDo方法无法被重写,也无法监控。

如果子类里使用this.BaseDo()或直接写BaseDo()来调用父类的功能,则父类的BaseDo方法会被重写,也可以监控。

    public class BaseClass
{
public virtual void BaseDo()
{
throw new Exception("BaseDo");//检测时请屏蔽
}
} public class ChildClass : BaseClass
{
public void ChildDo()
{
base.BaseDo();//不重写BaseDo方法,会throw,不能通过Verify检测
//this.BaseDo();//会重写BaseDo方法,不会throw,能通过Verify检测
}
} [TestClass]
public class Test
{
[TestMethod]
public void Testing()
{
var mock = new Mock<ChildClass>();
mock.Object.ChildDo();
mock.Verify(a => a.BaseDo(), Times.Once);
}
}

我估计这么设计是因为是想严格判断是base里的还是this里的方法,这么一想还挺有道理,比如:

    public class BaseClass
{
public virtual bool BaseDo()
{
return false;
}
} public class ChildClass : BaseClass
{
public override bool BaseDo()
{
return true;
} public bool ChildDo()
{
return base.BaseDo();//不会监控
//return this.BaseDo();//会监控
}
} [TestClass]
public class Test
{
[TestMethod]
public void Testing()
{
var mock = new Mock<ChildClass>();
var result = mock.Object.ChildDo();
mock.Verify(a => a.BaseDo(), Times.Once);
}
}

在这个例子里,base.BaseDo()和this.BaseDo()就是两个不同的方法,这时Moq判断的逻辑就更加清晰了

原则上,如果我们在代码里严格指定调用的是父类的方法(base.xxx()),那么Moq就不会去虚拟和监控父类的方法

-----------------------

参考资料:

https://www.cnblogs.com/haogj/archive/2011/07/22/2113496.html

https://www.cnblogs.com/darrenji/p/3869602.html

MOQ中CallBase的作用的更多相关文章

  1. web.xml中load-on-startup的作用

    如下一段配置,熟悉DWR的再熟悉不过了:<servlet>   <servlet-name>dwr-invoker</servlet-name>   <ser ...

  2. C#中构造函数的作用

    C#中构造函数的作用 共同点: 都是实例化对象,初始化数据的 默认构造是说所有的类都从祖先object那继承了空参的构造方法,你不写与写空参构造都存在,而有参数的构造一般是自己写的,写就有不写就没有, ...

  3. MySQL数据库中delimiter的作用概述

    以下的文章主要是向大家描述的是MySQL数据库中delimiter的作用是什么?我们一般都认为这个命令和存储过程关系不大,到底是不是这样的呢?以下的文章将会给你相关的知识,望你会有所收获. 其实就是告 ...

  4. js中getBoundingClientRect的作用及兼容方案

    js中getBoundingClientRect的作用及兼容方案 1.getBoundingClientRect的作用 getBoundingClientRect用于获取某个html元素相对于视窗的位 ...

  5. Linq中关键字的作用及用法

    Linq中关键字的作用及用法 1.All:确定序列中的所有元素是否都满足条件.如果源序列中的每个元素都通过指定谓词中的测试,或者序列为空,则为 true:否则为 false. Demo: 此示例使用 ...

  6. JAVA中protected的作用

    JAVA中protected的作用   1.public:public表明该数据成员.成员函数是对所有用户开放的,所有用户都可以直接进行调用 2.private:private表示私有,私有的意思就是 ...

  7. url中#号的作用

    url中#号的作用就是本页面位置跳转 比如这个url地址:http://www.aaaaa.com/index.html?ad=34&m=c#red red就是index.html页面的依哥位 ...

  8. Java中hashCode的作用

    转  http://blog.csdn.net/fenglibing/article/details/8905007 Java中hashCode的作用 2013-05-09 13:54 64351人阅 ...

  9. struts2 中 Actionsupport 的作用

    struts2 中 Actionsupport 的作用 Action 跟 Actionsupport 的区别     当我们在写action的时候,可以实现Action接口,也可以继承Actionsu ...

随机推荐

  1. theme-sodareload sublime编辑器主题插件还不错,不是语法高亮

    theme-sodareload   sublime编辑器主题还不错,不是语法高亮

  2. nginx配置url伪静态

    rewrite 规则 定向路径 重写类型; 举例: rewrite  (.*)/web/(.*)-(.*)-(.*).html$  $1/web/index.php?r=$2/$3/$4  last; ...

  3. 四十五.加密与解密 AIDE入侵检测系统 扫描与抓包

    一.加密与解密 1.1 常见的加密算法 对称加密:怎么加密,就怎么解密 DES Date Encryption Standard AES Advance Encryption Standard 非对称 ...

  4. 记一次netty的Hadoop和elasticsearch冲突jar包

    在一个项目中同时使用hbase和elasticsearch出现netty的jar包冲突的问题 事件: 在同一maven项目中使用hbase的同时又用了es 程序运行后出错 java.lang.NoSu ...

  5. codeforces#1120C. Compress String(dp+后缀自动机)

    题目链接: https://codeforces.com/contest/1120/problem/C 题意: 从前往后压缩一段字符串 有两种操作: 1.对于单个字符,压缩它花费$a$ 2.对于末尾一 ...

  6. [SDOI2015]序列统计(NTT+求原根)

    题目 [SDOI2015]序列统计 挺好的题!!! 做法 \(f[i][j]\)为第\(i\)个数前缀积在模\(M\)意义下为\(j\) 显然是可以快速幂的:\[f[2*i][j]=\sum\limi ...

  7. js即时函数在异步回调中的运用

    在编程中我们会接触到循环和异步编程的情况,这时异步回调执行逻辑就会出现问题.我们用setTimeout来模拟异步的: for(var i=0;i<3;i++){ setTimeout(funct ...

  8. wx.navigateTo和wx.redirectTo的不同

    wx.navigateTo保留当前页面,跳转到应用内的某个页面,使用wx.navigateBack可以返回到原页面. wx.redirectTo关闭当前页面,跳转到应用内的某个页面.就是不能返回了. ...

  9. mybatis-generator-gui如何打包成exe

    快速阅读: ​ 用wix和inno setup把mybatis-generator-gui 打包成exe和安装文件. 以后使用的时候方便,不用每次打开eclipse运行. 使用inno setup 5 ...

  10. java中 什么是反射?

    JAVA反射机制是在运行状态中,对于任意一个实体类,都能够知道这个类的所有属性和方法: 对于任意一个对象,都能够调用它的任意方法和属性:这种动态获取信息以及动态调用对象方法的功能称为java语言的反射 ...