【发布时间】:2011-10-11 04:02:33
【问题描述】:
有时我想测试方法中的中间值。但是方法不能拆分。所以我想知道JUnit是否只能将一个方法作为一个单元进行测试。如果我可以在方法中放置断点之类的东西,并获取本地值并对其进行断言,那就更好了。如果不可能,这种问题怎么解决。
【问题讨论】:
标签: android unit-testing testing junit tdd
有时我想测试方法中的中间值。但是方法不能拆分。所以我想知道JUnit是否只能将一个方法作为一个单元进行测试。如果我可以在方法中放置断点之类的东西,并获取本地值并对其进行断言,那就更好了。如果不可能,这种问题怎么解决。
【问题讨论】:
标签: android unit-testing testing junit tdd
添加断点并不是真正的单元测试,实际上根本不是测试。您可以将其称为检查,但没有检查驱动开发之类的东西。
无论如何,刚接触单元测试的人经常发现这个问题,他们想测试私有或本地值,让它成为一个变量或方法。事实上,当我开始 TDD 时,我自己已经完全被它分阶段了。但问题是,在单元测试中,目的是对特定功能和所有可能的结果进行黑盒测试。黑盒子里面发生的事情不是你关心的,你也不需要对它进行单元测试。
如果您想测试一个中间值,那么您的方法可能太长,应该分成两个或多个可测试的小方法。如果无法完成,那么您不必担心对其进行测试。
如果该中间值是从另一个公共方法获取它的值,那么它是您要在单独的单元测试中测试的 那个 方法,而不是您当前正在测试的方法中的值。
【讨论】:
您的问题导致了对 TDD 中 D 的解释。特别是当您使用 TDD 来表示“测试驱动设计”时(尽管有些人更喜欢“测试驱动开发”这个短语)。
正如@Shahzeb 指出的那样,也许你的方法太长了,应该分成两种方法,一种产生中间值,另一种将其作为输入。我们以这种方式思考代码的倾向实际上是由测试驱动。我们代码的设计更好,因为我们为了能够测试它们而分离关注点。因此,您提出了一个很好的问题(其简短的回答是“否”),这些问题可以让 TDD 改进我们的设计。
【讨论】:
这个想法是您根本不测试私有(中间)值,因为它在外部并不重要(这就是您明智地将其保持私有的原因。)私有值表示您设置的对象中的某些状态现在的意图是它会影响将来对您的公共接口的调用,对吗?所以改变你的一个测试来打两个电话。让第一次调用执行任何需要的操作,按照您认为的方式设置状态,然后进行第二次调用,并查看设置该变量时结果是否符合您的预期。如果它真的是私有的,那么单元测试它的值是什么并不重要——只要它在正确的时间正确地产生所需的结果。但是这个建议带有一个警告:它正在悄悄进入你可能要求单元测试做的比一个单元的测试价值更多的领域。
另一个观察:您说您的方法“不能拆分”,但没有提供解释原因。如果您无法更改设计,听起来更像是您可能试图将单元测试插入遗留代码,而不是执行测试驱动开发。没关系,您不必在这里放弃 TDD,但也许还有其他方法需要考虑。一旦你通过了测试,在 TDD 中,这就是你需要重构方法的部分。你在谈论一个中间值的事实表明你的方法有太多的责任。考虑使用提取方法将功能的更简洁部分封装成更小、可测试的服务方法。
如果这不是您想要完成的任务,那么您尝试执行的测试可能是“想得太大”了。也许您尝试做的测试更多的是验收测试。同样,这很好,验收测试也很重要,但它不再是真正的单元测试了。
【讨论】: