什么时候在C#unit testing中使用模拟与伪装?

任何人都可以拿出指导方针,build议select嘲笑还是伪造的理想场景,即手动设置要领?

我对如何处理这种情况感到困惑。

那么你有几件事情你需要理清。 你有两个基本的东西你需要知道:命名和最佳实践。

首先,我想给你一个伟大的testing者,罗伊·奥谢罗夫伟大的video资源:

unit testing评论由Roy Osherove

他开始说他已经对几个开源项目附带的testing工具进行了一些评论。 你可以在这里find这些: http : //weblogs.asp.net/rosherove/archive/tags/TestReview/default.aspx

这些基本上都是video评论,他会带你通过这些testing用具,告诉你什么是好的,什么是坏的。 很有帮助。

罗伊也有一本我明白的书很好。

命名法

这个播客将帮助非常 : http : //www.hanselminutes.com/default.aspx? showID = 187

不过,我会用播客的话来解释一下(Hanselminutes介绍音乐是可怕的):

基本上,你用隔离框架 (如Moq,Rhino Mocks,Type Mock等)做的所有事情都叫做假货

伪造是在testing过程中使用的对象,您正在testing的代码可以调用代替生产代码。 伪造是用来隔离你正在testing的代码与你的应用程序的其他部分。

有(主要)两种types的假货存根嘲笑

模拟是一个假的,你放在适当的位置,以便你正在testing的代码可以调用它,并且你声明这个调用是用正确的参数进行的。 下面的示例使用Moq隔离框架来做到这一点:

[TestMethod] public void CalculateTax_ValidTaxRate_DALCallIsCorrect() { //Arrange Mock<ITaxRateDataAccess> taxDALMock = new Mock<ITaxRateDataAccess>(); taxDALMock.Setup(taxDAL => taxDAL.GetTaxRateForZipCode("75001")) .Returns(0.08).Verifiable(); TaxCalculator calc = new TaxCalculator(taxDALMock.Object); //Act decimal result = calc.CalculateTax("75001", 100.00); //Assert taxDALMock.VerifyAll(); } 

一个存根与模拟几乎相同,不同之处在于你要确保你正在testing的代码从它的调用中获取一致的数据(例如,如果你的代码调用一个数据访问层,一个存根将返回假的数据),但是你不会对存根本身断言。 也就是说,您并不在意validation该方法是否称为您的假数据访问层 – 您正在尝试testing其他内容。 您提供了存根以获取您要testing的方法以独立工作。

这是一个存根的例子:

 [TestMethod] public void CalculateTax_ValidTaxRate_TaxValueIsCorrect() { //Arrange Mock<ITaxRateDataAccess> taxDALStub = new Mock<ITaxRateDataAccess>(); taxDALStub.Setup(taxDAL => taxDAL.GetTaxRateForZipCode("75001")) .Returns(0.08); TaxCalculator calc = new TaxCalculator(taxDALStub.Object); //Act decimal result = calc.CalculateTax("75001", 100.00); //Assert Assert.AreEqual(result, 8.00); } 

注意,我们正在testing方法的输出,而不是方法调用另一个资源的事实。

Moq实际上并没有在模拟和存根之间做出区别(注意两者都被声明为Mock<T> ),但是这里的用法在确定types时很重要。

希望这有助于你的直线。

你想testing一个代码块,对,让我们来说一个方法。 您的方法从http url下载文件,然后将该文件保存在磁盘上,然后将该文件发送到磁盘上。 所有这三个动作当然都是你的方法调用的服务类,因为这样他们很容易被嘲笑。 如果你不嘲笑这些,你的testing会下载东西,访问磁盘,并且每次运行testing时都会收到邮件。 那么你不仅仅是testing方法中的代码,你还在testing下载,写入磁盘和发送邮件的代码。 现在,如果你嘲笑这些,你只是testing方法代码。 你也可以模拟一个下载失败的例子,看看你的方法的代码行为是否正确。

至于伪装,我通常假冒那些只是持有价值的类,并没有太多的逻辑。 如果你发送一个包含一些值的对象,在方法中被修改,你可以在testing中读取它,看看这个方法是否正确。

当然,这些规则可以(有时也必须)稍微弯曲,但一般的思维方式是testing你的代码,只testing你的代码。

来自鲍勃·马丁(Bob Martin) 的小嘲笑者(Little Mocker)在这个话题上是非常好的读物。

[…]很久以前,一些非常聪明的人写了一篇文章,介绍和定义了“模拟对象”这个词。 很多其他人阅读并开始使用这个术语。 其他没有读过这篇文章的人听到这个词,开始使用这个术语的意思更为广泛。 他们甚至把这个词变成动词。 他们会说:“让我们嘲笑这个对象”,或者“我们有很多嘲弄的事情要做”。

文章解释了嘲笑,假货,间谍和存根之间的区别。