我正在使用 C#、NUnit 和 Rhino Mocks 编写单元测试。
以下是我正在测试的课程的相关部分:
public class ClassToBeTested
{
private IList<object> insertItems = new List<object>();
public bool OnSave(object entity, object id)
{
var auditable = entity as IAuditable;
if (auditable != null) insertItems.Add(entity);
return false;
}
}
我想在调用 OnSave 后测试 insertItems 中的值:
[Test]
public void OnSave_Adds_Object_To_InsertItems_Array()
{
Setup();
myClassToBeTested.OnSave(auditableObject, null);
// Check auditableObject has been added to insertItems array
}
对此的最佳实践是什么?我考虑过将 insertItems 添加为具有公共 get 的属性,或将 List 注入 ClassToBeTested 中,但不确定我是否应该出于测试目的修改代码。
我读过很多关于测试私有方法和重构的文章,但这是一个如此简单的类,我想知道什么是最好的选择。
简单的回答是,您永远不应该从单元测试中访问非公开成员。它完全违背了拥有测试套件的目的,因为它将您锁定在您可能不希望保持这种状态的内部实现细节中。
较长的答案涉及到接下来要做什么?在这种情况下,重要的是要理解为什么实现是这样的(这就是为什么 TDD 如此强大,因为我们使用测试来specify预期的行为,但我感觉你没有使用 TDD)。
就您而言,首先想到的问题是:“为什么将 IAuditable 对象添加到内部列表中?”或者,换句话说,“预期的结果是什么?外部可见此实施的结果?”根据这些问题的答案,that's你需要测试什么。
如果您将 IAuditable 对象添加到内部列表中,因为您稍后想要将它们写入审核日志(只是一个大胆的猜测),那么调用写入日志的方法并验证是否写入了预期的数据。
如果您将 IAuditable 对象添加到内部列表中是因为您想要收集针对某种后续约束的证据,那么请尝试对其进行测试。
如果您添加代码没有任何可衡量的原因,请再次删除它:)
重要的是,它对测试非常有利behavior代替执行。它也是一种更强大且可维护的测试形式。
不要害怕修改您的被测系统 (SUT) 以使其更具可测试性。只要您的添加在您的领域中有意义并遵循面向对象的最佳实践,就不会有问题 -你只需遵循开闭原则.
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)