【问题标题】:Mock Verify/VerifyAll before or after Assertion在断言之前或之后模拟验证/验证所有
【发布时间】:2010-10-26 01:15:55
【问题描述】:

我在编写测试时已经习惯了遵循代码模式

public void TestMethod_Condition_Output()
{
    //Arrange----------------
    Mock<x> temp = new Mock<x>();
    temp.setup.......

    //Act--------------------
    classinstance.TestMethod()

   //Assert------------------

   temp.VerifyAll();
   Assert.AreNotEqual(.....)    
}

我习惯于在执行断言之前执行 VerifyAll()。但最近在一些在线示例中,我看到有人先做 Assertion,然后再做 VerifyAll,如果有的话。我确实觉得我的方式是正确的方式,除非我错过了什么。

如果我遗漏了什么,请提醒我。

【问题讨论】:

    标签: c# unit-testing mocking moq


    【解决方案1】:

    在我看来,验证应该在断言之后。我希望断言接近被测方法的调用,因为它们正在记录方法的作用。模拟调用的验证详细说明了类如何使用它的依赖项。这对于直接绑定到方法本身并不重要。

    从某种意义上说,依赖项的模拟变成了实际测试本身的包装。这使测试更容易理解(对我来说,无论如何,YMMV)。然后我的测试遵循这个模式:

    安排

    • 模拟
    • 为依赖项设置期望
    • 设置预期结果
    • 创建待测类

    行动

    • 调用被测方法

    断言

    • 断言实际结果与预期结果相符
    • 验证是否满足预期

    我不知道我会对此感到迂腐,但这是对我来说最有意义的顺序。

    【讨论】:

    • 公平评论。连我都被束缚住了。在我的场景 [Verify before Assertion] 中,它确实确保依赖项是否设置正确并且没有问题。当我的控制器执行一些昂贵的数据库调用时,重要的是在断言之前运行验证以确保它真的被模拟而不是先执行那些少数断言。无论哪种方式,我觉得我们的两种方法都是有效的
    • @Nimesh - 我看不出在断言之前进行验证实际上有助于确保在进行昂贵的数据库调用之前对方法进行模拟。当然,如果它们没有被嘲笑,那么在您进行验证时,您已经进行了 db 调用。一旦单元测试通过,它就不应该有任何区别。我错过了什么吗?
    • 不,你没有错过任何东西。是的,一旦通过了单元测试,我们使用哪个顺序都没有关系。但是,是的,在开发过程中,它会很有用。但是,我得到了答案,顺序无关紧要。谢谢大佬。
    【解决方案2】:

    在 AAA 风格的测试中,我不使用 VerifyAll,而是在测试单元中显式调用验证方法。在排列区域内,我只设置需要返回值的方法。

    以 Rhino 为例...

    //Arrange
    mockedInterface.Stub(x => x.SomeMethod1()).Returns(2);
    
    ...
    
    //Assert
    mockedInterface.AssertWasCalled(x => x.SomeMethod1());
    mockedInterface.AssertWasCalled(x => x.SomeMethod2());
    Assert.AreEqual(...); // stanmdard NUnit asserttions
    

    如果 SomeMethod2() 没有返回任何内容,我不需要设置对它的预期调用。

    使用 Loose 模拟没有真正需要调用 VerifyAll,因为对其他方法的调用不会使测试失败(除非需要返回,否则在 Arrange 部分中需要它)。

    断言的数量应该保持在最低限度(如果它变得太大,则创建更多测试)并且它们的顺序也不应该真正重要。

    【讨论】:

    • 我正在使用 Moq 进行模拟。但是一般的解释和它们的顺序不应该真正重要地断言我的假设。我是这么认为的,但在最佳实践方面,我自己更喜欢在断言之前进行验证。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2016-10-21
    • 2019-06-25
    • 1970-01-01
    • 2018-10-06
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多