C# &引用;“短路”;有最小起订量的无效方法?

C# &引用;“短路”;有最小起订量的无效方法?,c#,unit-testing,mocking,methods,moq,C#,Unit Testing,Mocking,Methods,Moq,我的团队最近决定使用Moq作为我们的模拟框架,因为它具有极大的灵活性和高度可读的语法。由于我们是新手,我在一些看似简单的问题上结结巴巴——搜索(这里,谷歌,等等)找到了大量关于Moq其他细微差别的讨论,但不一定是我所追求的,少数几个看似相关的问题已经变成了红鲱鱼 我们正在测试一个具有外部依赖性的类(准确地说是Amazon SimpleDb),但不希望我们的测试绑定到一个活动连接。一种特殊的方法: 应用一些“业务”逻辑 如果合适,通过我们构建的提供程序调用对SDB的调用,我们将其称为SaveIt

我的团队最近决定使用Moq作为我们的模拟框架,因为它具有极大的灵活性和高度可读的语法。由于我们是新手,我在一些看似简单的问题上结结巴巴——搜索(这里,谷歌,等等)找到了大量关于Moq其他细微差别的讨论,但不一定是我所追求的,少数几个看似相关的问题已经变成了红鲱鱼

我们正在测试一个具有外部依赖性的类(准确地说是Amazon SimpleDb),但不希望我们的测试绑定到一个活动连接。一种特殊的方法:

  • 应用一些“业务”逻辑
  • 如果合适,通过我们构建的提供程序调用对SDB的调用,我们将其称为
    SaveItem()
我想对此进行单元测试,这样我们就可以设置所需的上下文,并确保调用了
SaveItem()
,但实际上不会调用
SaveItem()
(因为a)SDB的供应商是一个未完全水合的模拟供应商,可能会爆炸;B)我不想为该交易支付成百上千的费用)

在处理返回值的方法时,这是微不足道的

mockDb.Setup(d => d.GiveMeSomething()).Returns("Foo");
但是,在我上面概述的情况下,我的“
SaveItem()
”方法无效,因此使用Moq的
Returns()
方法的选项不可用。虽然我可以设置一个回调来验证调用了
SaveItem()
,但我似乎无法让它实际不做任何事情

天真/充满希望,我认为以下方法会奏效,但它似乎仍然调用了该方法:

mockDb.Setup(d => d.SaveItem(It.IsAny<object>()));
mockDb.Setup(d=>d.SaveItem(It.IsAny());
所以百万美元的问题是:以下虚构代码的最低起订量是多少

mockDb.Setup(d => d.SaveItem(It.IsAny<object>())).STOP_RIGHT_HERE();
mockDb.Setup(d=>d.SaveItem(It.IsAny())。在此处停止();
如果
SaveItem()
方法是虚拟的或抽象的,并且您没有设置
Callbase=true
,那么应该通过模拟重新实现该方法,使其不执行任何操作

您应该能够做到:

mockDb.Setup(d => d.SaveItem(It.IsAny<object>())).Verifiable();

...  test here ...

mockDb.Verify();
mockDb.Setup(d=>d.SaveItem(It.IsAny()).Verifiable();
...  在这里测试。。。
mockDb.Verify();

编辑以澄清这种情况,该测试是针对浮动的“业务”类,而不是针对实际的SimpleDB实现。SimpleDB实现在其他地方进行了测试,这里,这就是我正在模仿的。完美!我完全不知道Verifiable()/Verify()这类东西的用意是什么,而且没有更正式的文档,我甚至不知道如何阅读该领域的线程和帖子。只是尝试一下,我现在有了针对这种情况的正面和负面测试用例。多谢+1.此外,您还可以通过调用mockDb来验证所有调用,而不考虑Verifiable()标志。VerifyAll()是否可能为其他场景扩展此答案,即方法既不是虚拟的,也不是抽象的?@leon它将同样适用于非抽象的。但是,它必须是虚拟的,Moq才能模拟它(它是子类和重写)