RSpec:测试logger消息的块语法

时间:2014-01-21 10:31:29

标签: ruby logging rspec

我目前以下列方式使用记录器:

def log_stuff
  logger.info { 'Info log message' }
  logger.debug { expesive_action }
end

但我想知道记录器是否收到了RSpec的正确消息。

如果我只是将记录行传递给输入,这很容易:

# logger.info('Info log message')
expect(logger_mock).to receive(:info).with('Info log message')

但我无法找到一种方法,我可以用块语法做这样的事情。

我特别想使用这种语法,这样只有在日志级别设置为DEBUG时才会调用expensive_action

2 个答案:

答案 0 :(得分:4)

这不是 困难,虽然比香草的期望更棘手:

  expect(logger_mock).to receive(:info) do |&block|
    expect(block.call).to eq('Info log message')
  end

在这种情况下,您的规范中的&block只是您在logger.info电话中遇到的阻止。因此,您必须显式调用它,然后在返回值上设置另一个期望值。这就是我的方式,至少。

答案 1 :(得分:0)

不幸的是,它非常棘手,因为该块是惰性评估的。

有时你可以通过在较低级别进行嘲笑来解决这个问题。例如,info内部调用add传递日志类型。但是,即使在这种情况下,模拟添加对您没有帮助,因为块是逐字传递的,并且它没有被评估。

此时,您可能希望存根expensive_action的执行并检查是否已调用该操作。当然,如果你只是在块中返回一个字符串,这个解决方案将不起作用,但只有当你调用另一个方法时才可以模拟。