Ruby rspec 模拟一个 class

Ruby rspec Mocking a class

我有一个包含两个 class 的文件。

class LogStash::Filters::MyFilter< LogStash::Filters::Base

class LogStash::JavaMysqlConnection

JavaMysqlConnection 有方法 initializeselectMyFilter class 正在使用它,您可能已经猜到它用于查询数据库。

如何将 initializeselect 方法分别模拟为 return nil 和数组?

我尝试使用:

before(:each) do
  dbl = double("LogStash::JavaMysqlConnection", :initialize => nil)
end

但这没有用,因为我仍然看到通信 link 失败。

我有 rspec 版本 2.14.8

提前致谢。 PS。我是 Ruby

的新手

差(工作):Read more as to why exactly it is a bad practice

allow_any_instance_of(LogStash::JavaMysqlConnection)
  .to receive(:select)
  .and_return([])

好:

let(:logstash_conn) { instance_double(LogStash::JavaMysqlConnection) }

allow(LogStash::JavaMysqlConnection)
  .to receive(:new)
  .and_return(logstash_conn)

allow(logstash_conn)
  .to receive(:select)
  .and_return([])

Docs

RSpec

根据 Andrey 的回复,对我有用的解决方案是:

 before(:each) do
    mock_sql = double(:select=> sql_select_return)
    allow(LogStash::JavaMysqlConnection).to receive(:new).and_return(mock_sql)
end

使用RSpecstub_const

describe 'No User' do
  let(:user)       { double }
  let(:attributes) { { name: 'John' } }

  before do
    stub_const 'User', instance_double('User', new: user)
  end

  it 'creates user' do
    expect(user).to receive(:update!).with(attributes)

    User.new.update!(attributes)
  end
end