我正在尝试了解测试驱动设计,特别是 RSpec。但我在使用 RSpec 书中的一些示例时遇到了麻烦。
在书中,我们测试 $STDOUT 上的输出,如下所示:
output = double('output')
game = Game.new
output.should_receive(:puts).with('Welcome to Codebreaker!')
game.start()
嗯,这确实有效。但我到底为什么要关心 Game 对象是否使用 put() 方法呢?如果我将其更改为 print(),它真的会破坏测试吗?而且,更重要的是,这是否违背了 TDD 的原则之一——我应该测试方法的作用(设计)而不是方法的作用(实现)?
有什么方法可以编写一个测试来测试 $STDOUT 上最终的内容,而不查看什么方法将其放在那里?
创建一个能够写出状态的显示类。
您的生产代码将使用此显示对象,因此您可以自由更改写入 STDOUT 的方式。当您的测试依赖于抽象时,该逻辑将只有一个位置。
例如:
output = stub('output')
game = Game.new(output)
output.should_receive(:display).with('Welcome to Codebreaker!')
game.start()
虽然您的生产代码将包含诸如
class Output
def display(message)
# puts or whatever internally used here. You only need to change this here.
end
end
我将通过执行以下操作来使此测试通过:
def start
@output.display('Welcome to Codebreaker!')
end
这里的生产代码并不关心输出如何显示。现在抽象已经到位,它可以是任何形式的显示。
上述所有理论都与语言无关,并且很有效。您仍然模拟您不拥有的东西,例如第三方代码,但您仍在测试您是否通过抽象来执行手头的工作。
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)