同一类中的单元测试(使用条件编译)?

时间:2012-06-14 15:27:38

标签: c# .net unit-testing

我知道(并同意)将单元测试放在单独的程序集中的常用参数。但是,最近我遇到了一些我真的想要测试私有方法的情况。有问题的幕后逻辑足够复杂,以至于测试公共和内部接口并不能完成工作。针对班级公共界面的测试感觉过于紧张,我看到几个针对私人的测试可以更简单有效地完成工作。

过去我通过制作我需要测试protected的东西,并创建一个我可以用来在测试框架中获取它的子类来解决这些情况。但是对于应该是sealed的类,这种方法效果不佳。更不用说用所有脚手架膨胀测试框架了。

所以我正在考虑这样做:在课堂上放置一些测试,他们可以在私人成员那里学习。但是使用'#if DEBUG`将它们排除在生产代码之外。

这看起来是个好主意吗?

3 个答案:

答案 0 :(得分:9)

在任何人问之前......

OP问题的解决方案是将IoC与DI正确合并,无需完全测试私有方法(如Joel Martinez noted)。正如已经提到multiple times,单位测试私人成员不是

但是,有时您无法更改代码(旧系统,破坏更改的风险 - 您的名字),也不能使用允许私有成员的工具测试(如Typemock,这是付费产品)。对于这种情况,你可以不测试或偷工减料。我认为这是OP面临的情况。


私人方法测试讨论放在一边......

请记住,您可以使用反射来访问和调用私人成员。

在我看来,在类本身放置条件调试是一个相当糟糕的主意 - 它会将 noise (如同,无关的内容)添加到类代码中。当然,它将在发布时消失,但你(可能还有其他程序员)将不得不在日常基础上处理它。

我意识到你的想法在纸面上听起来不错 - 用条件调试包装的简单测试。但实际上,测试很快就会使用额外变量(那些也必须放在类代码中),一些实用程序(额外引用,自定义类型), 测试框架(甚至更多参考资料),什么不是。这一切都必须以某种方式连接到类代码。把它们放在一起,你很快就会得到一个无法想象的怪物

你确定要处理那个吗?特别是考虑到将基于反射的简单实用程序放在一起可能并不那么难。

答案 1 :(得分:7)

您提到的所有内容都可以通过两个概念来解决:Single Responsibility PrincipleDependency Injection。听起来你需要简化你的课程。请注意,这并不意味着课程必须提供更少的价值,它只是意味着内部需要更简单,而某些功能可能必须委托给其他人。

答案 2 :(得分:4)

如果您需要独立于类的公共API测试此方法,那么它听起来像是从类本身中删除的候选者。

你可以说这个类在私有方法上是 依赖 (正如需要从类公共API中单独测试它一样明显可见)。

如果通过测试类型类型的公共API无法满足此依赖关系,则让该类将此依赖关系委托给另一种类型。您可以在内部实例化此类型,也可以注入/解析此类型。

这个新类型然后有自己的单元测试,因为它的公共API将表示以前的私有方法。