unit testing – 让unit testing调用其他unit testing是不好的forms

我有一个名为TestMakeAValidCall()的unit testing。 它测试我的手机应用程序拨打有效电话。

我即将编写另一个名为TestShowCallMessage()的测试,该测试需要为测试进行有效调用。 在该测试中调用TestMakeAValidCall()是不好的forms?

作为参考,这是我的TestMakeAValidCall()测试。

  [TestMethod] public void TestMakeAValidCall() { //Arrange phone.InCall = false; phone.CurrentNumber = ""; // Stub the call to the database data.Expect(x => x.GetWhiteListData()). Return(FillTestObjects.GetSingleEntryWhiteList()); // Get some bogus data string phoneNumber = FillTestObjects.GetSingleEntryWhiteList(). First().PhoneNumber; // Stub th call to MakeCall() so that it looks as if a call was made. phone.Expect(x => x.MakeCall(phoneNumber)). WhenCalled(invocation => { phone.CurrentNumber = phoneNumber; phone.InCall = true; }); //Act // Select the phone number deviceControlForm.SelectedNumber = phoneNumber; // Press the call button to make a call. deviceMediator.CallButtonPressed(); //Assert Assert.IsTrue(phone.InCall); Assert.IsTrue(phone.CurrentNumber == phoneNumber); } 

将设置重构为另一个方法,并从两个测试中调用该方法。 测试不应该调用其他测试。

恕我直言,你应该做以下其中一件事:

  • 创建一个返回有效调用的方法,并为两个测试分别使用它(不是一个调用另一个)
  • 模拟ShowCallMessageTest的有效调用

我认为这是一个坏主意。 您希望您的unit testing仅测试一件事和一件事。 不是通过其他测试创建调用,而是模拟调用并将其作为参数传递。

提出一个反点:

我坚信精心设计的unit testing应该相互依赖!

当然,只有当测试框架知道这些依赖关系时才有意义,这样当依赖关系失败时它就可以停止运行依赖测试。 更好的是,这样的框架可以将夹具从测试传递到测试,这样可以构建在不断增长和扩展的夹具上,而不是为每次单个测试从头开始重建。 当然,进行缓存是为了注意当多个测试取决于同一个例子时,不会引入副作用。

我们在JUnit的JExample扩展中实现了这个想法。 目前还没有C#端口,虽然有Ruby和Smalltalk的端口…… 最近发布的PHPUnit提到了我们的想法:依赖关系和夹具重用 。

PS: 人们也将它用于Groovy 。

unit testing应根据定义测试代码的一个单元/function。 让它调用其他unit testing使它测试多个单元。 我把它分解为个别测试。

是的 – unit testing应该是分开的,并且应该只测试一件事(或者至少是少量紧密相关的事情)。 顺便说一句,在你的测试方法中调用data.Expect和phone.Expect正在创建期望而不是存根调用,如果你重构,这会使你的测试变得脆弱……

单元与模块….我们还认为测试应该依赖于可重用的方法,并且应该在api级别测试测试类的集成。 许多人只测试一个类,但很多错误都是在类级别之间的集成。 我们还使用verifydesign来保证api不依赖于实现。 这允许您在不接触测试的情况下重构整个组件/模块(我们实际上经历了一次并且它工作得很好)。 当然,任何体系结构更改都会强制您重构测试,但至少模块中的设计更改不会导致测试重构工作(除非您更改api的行为当然隐含地像触发更多事件而不是以前那样“无论如何都会“变成api”。