MiniTest中的方法期望

时间:2012-06-16 22:34:03

标签: ruby-on-rails ruby minitest

我正在尝试为ActiveRecord编写测试 - 而Rails使用MiniTest进行测试,所以我没有选择测试框架。我要测试的条件是这个(来自db:创建rake任务,为了这个例子的目的拉入一个方法):

def create_db
  if File.exist?(config['database'])
    $stderr.puts "#{config['database']} already exists"
  end
end

所以,我想测试$ stderr如果File存在则收到puts,否则不会。在RSpec中,我会这样做:

File.stub :exist? => true

$stderr.should_receive(:puts).with("my-db already exists")

create_db

MiniTest中的等价物是什么? assert_send似乎没有按照我的预期行事(并且那里没有任何文档 - 它应该在执行之前去,比如should_receive,还是之后?)。我想我可以在测试期间暂时使用模拟设置$ stderr,但$ stderr只接受响应write的对象。你不能在mocks上存根方法,我不想在我的stderr mock上设置write方法的期望 - 这意味着我正在测试一个我正在嘲笑的对象。

我觉得我没有在这里使用MiniTest正确的方式,所以一些指导将不胜感激。

更新:这是一个有效的解决方案,但它设置期望:write,这是不对的。

def test_db_create_when_file_exists
  error_io = MiniTest::Mock.new
  error_io.expect(:write, true)
  error_io.expect(:puts, nil, ["#{@database} already exists"])
  File.stubs(:exist?).returns(true)

  original_error_io, $stderr = $stderr, error_io

  ActiveRecord::Tasks::DatabaseTasks.create @configuration

ensure
  $stderr = original_error_io unless original_error_io.nil?
end

1 个答案:

答案 0 :(得分:0)

因此,事实证明Rails将Mocha与Minitest结合使用,这意味着我们可以利用Mocha更好的消息预期。工作测试如下:

def test_db_create_when_file_exists
  File.stubs(:exist?).returns(true)

  $stderr.expects(:puts).with("#{@database} already exists")

  ActiveRecord::Tasks::DatabaseTasks.create @configuration
end