Rspec 3.0如何模拟替换参数但没有返回值的方法?

时间:2014-04-18 02:08:31

标签: ruby rspec mocking stubbing

我已经搜索了很多,虽然看起来很基本,却无法解决这个问题。这是我想要做的简化示例。

创建一个简单的方法,可以执行某些操作但不返回任何内容,例如:

class Test
  def test_method(param)
    puts param
  end
  test_method("hello")
end

但在我的rspec测试中,我需要传递一个不同的参数,例如"再见"而不是"你好。"我知道这与存根和模拟有关,而且我已查看文档但无法弄清楚:https://relishapp.com/rspec/rspec-mocks/v/3-0/docs/method-stubs

如果我这样做:

@test = Test.new
allow(@test).to_receive(:test_method).with("goodbye")

它告诉我存根一个默认值,但我无法弄清楚如何正确地做到这一点。

错误讯息:

received :test_method with unexpected arguments
  expected: ("hello")
  got: ("goodbye")
Please stub a default value first if message might be received with other args as well.     

我正在使用rspec 3.0,并调用类似

的内容
@test.stub(:test_method)

是不允许的。

2 个答案:

答案 0 :(得分:12)

答案 1 :(得分:1)

对于您的示例,由于您不需要测试test_method的实际结果,只有在传递puts时调用param,我只会通过设置进行测试提高期望并运行方法:

class Test
  def test_method(param)
    puts param
  end
end

describe Test do
  let(:test) { Test.new }

  it 'says hello via expectation' do
    expect(test).to receive(:puts).with('hello')
    test.test_method('hello')
  end

  it 'says goodbye via expectation' do
    expect(test).to receive(:puts).with('goodbye')
    test.test_method('goodbye')
  end
end

您尝试做的是在方法上设置test spy,但我认为您正在设置方法存根一个级别太高(在test_method本身而不是putstest_method的调用。如果你将存根放在puts的调用上,你的测试应该通过:

describe Test do
  let(:test) { Test.new }

  it 'says hello using a test spy' do
    allow(test).to receive(:puts).with('hello')
    test.test_method('hello')
    expect(test).to have_received(:puts).with('hello')
  end

  it 'says goodbye using a test spy' do
    allow(test).to receive(:puts).with('goodbye')
    test.test_method('goodbye')
    expect(test).to have_received(:puts).with('goodbye')
  end
end