当前位置:  开发笔记 > 编程语言 > 正文

TDD:Stub,Mock或以上都不是

如何解决《TDD:Stub,Mock或以上都不是》经验,为你挑选了1个好方法。

我正在尝试将TDD应用于我的一个简单项目.一些细节(以及之前的问题)在这里:

TDD:帮助编写Testable类

具体是我有一个PurchaseOrderCollection类,它有一个私有的PurchaseOrders列表(在构造函数中传入),而PurchaseOrders有一个布尔属性IsValid.PurchaseOrderCollection具有属性HasErrors,如果列表中的任何PurchaseOrders将IsValid设置为false,则返回true.这是我想测试的逻辑.

[TestMethod]
public void Purchase_Order_Collection_Has_Errors_Is_True_If_Any_Purchase_Order_Has_Is_Valid_False()
{
    List orders = new List();

    orders.Add(new PurchaseOrder(--some values to generate IsValid false--));
    orders.Add(new PurchaseOrder(--some values to generate IsValid true--));

    PurchaseOrderCollection collection = new PurchaseOrderCollection(orders);

    Assert.IsTrue(collection.HasErrors);
}

这与我之前的问题类似,因为这个测试太过耦合了,我必须知道什么使得PurchaseOrder IsValid为false或者true才能通过测试,而这个测试真的不应该关心.问题是不同的(imo)因为类本身不是问题.

基本上我希望能够在不知道任何有关PurchaseOrder的内容的情况下声明具有IsValid false或true的PurchaseOrder.

根据我有限的TDD知识,这是你使用Stubs或Mocks的东西.我的主要问题是,这是正确的吗?或者我应该使用不同的方法吗?或者我是完全有缺陷的,我只是在写这个测试并且认为它错了?

我最初的想法是只使用某种模拟框架并创建一个始终返回true或false的PurchaseOrder.从我读过的内容来看,我需要声明IsValid是虚拟的.所以我的第二个想法是改变它以添加IPurchaseOrder作为PurchaseOrder的接口,并创建一个始终返回false或true的假PurchaseOrder.这些都是有效的想法吗?

谢谢!



1> Dale Ragan..:

无论是创建存根还是模拟,您都在正确的轨道上.我更喜欢使用Mocking框架.

使用模拟框架的工作原理是你想要模拟你的PurchaseOrder类,从而抽象出它的实现.然后设置调用IsValid的期望值以及调用它时返回此值.

使用Moq的示例,如果您使用的是C#3.0和.NET Framework 3.5:

[TestMethod]
public void Purchase_Order_Collection_Has_Errors_Is_True_If_Any_Purchase_Order_Has_Is_Valid_False()
{    
    var mockFirstPurchaseOrder = new Mock();
    var mockSecondPurchaseOrder = new Mock();

    mockFirstPurchaseOrder.Expect(p => p.IsValid).Returns(false).AtMostOnce();
    mockSecondPurchaseOrder.Expect(p => p.IsValid).Returns(true).AtMostOnce();

    List purchaseOrders = new List();
    purchaseOrders.Add(mockFirstPurchaseOrder.Object);
    purchaseOrders.Add(mockSecondPurchaseOrder.Object);

    PurchaseOrderCollection collection = new PurchaseOrderCollection(orders);

    Assert.IsTrue(collection.HasErrors);
}

编辑:
这里我使用了一个界面来创建PurchaseOrder的模拟,但你没有.您可以将IsValid标记为虚拟并模拟PurchaseOrder类.我的经验法则是哪种方式首先使用虚拟.只是为了创建一个界面,所以我可以在没有任何架构原因的情况下模拟一个对象,这对我来说是一种代码味道

推荐阅读
ifx0448363
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有