1

下面是根据RSpec book中的示例传递代码。

describe "#start"块中,为什么should_receive...'Welcome to Codebreaker!来之前game.start

在我看来,在调用 start 方法之前不会放置文本。但是,如果我重新排序这两行,测试将不再通过。

为什么是这样?

lib/codebreaker.rb

module Codebreaker
  class Game
    def initialize(output)
      @output = output
    end

    def start
      @output.puts "Welcome to Codebreaker!"
    end
  end
end

规范/codebreaker_spec.rb

require 'codebreaker'

module Codebreaker
  describe Game do
    let(:output) { double('output') }
    let(:game) { Game.new(output) }

    describe "#start" do
      it "sends a welcome message" do
        output.should_receive(:puts).with('Welcome to Codebreaker!')
        game.start
      end
    end
  end
end
4

2 回答 2

2

来自官方文档:https ://www.relishapp.com/rspec/rspec-mocks/v/2-5/docs/message-expectations/expect-a-message

“使用 should_receive() 设置接收者应该在示例完成之前收到消息的期望。”

阅读上面两个粗体字你可能对这个方法有更好的理解。当你设置should_receive()时,它建立了一个期望,并会在这个例子中观察下面的代码运行(它阻塞)

所以这个方法只有在你之前设置好之后运行代码才有意义。这应该能够解释你的问题。

于 2013-05-02T02:54:43.587 回答
1

在这个街区

  it "sends a welcome message" do
    output.should_receive(:puts).with('Welcome to Codebreaker!')
    game.start
  end

它期望输出接收带有“欢迎使用 Codebreaker!”的放置。好?因此,在创建期望之后,代码运行并且测试通过。

如果您更改行的顺序,您将运行代码,然后您创建一个不会发生的期望,因为输出将永远不会收到“puts”,并且测试将失败。

使用 rspec,您应该始终按照该顺序创建期望并使其发生

于 2013-05-02T02:00:35.240 回答