简体   繁体   English

RSpec:测试邮件程序只调用一次

[英]RSpec: Testing that a mailer is called exactly once

I have a Mailer that looks something like this: 我有一个看起来像这样的Mailer

class EventMailer < BaseMailer
  def event_added(user_id, event_id)
    # do stuff and email user about the event
  end
end

I'm calling this EventMailer like this from inside the Event class: 我在Event类中调用了这个EventMailer

class Event < Task
  def notify_by_email(user)
    EmailLog.send_once(user.id, id) do
      EventMailer.delay(queue: 'mailer').event_added(user.id, id)
    end
  end
end

where EmailLog is a class that logs sent emails. EmailLog是一个记录已发送电子邮件的类。 .delay is added by Sidekiq. .delay由Sidekiq添加。

But when I try to test that #notify_by_email is called only once per event and user, my spec fails: 但是当我尝试测试每个事件和用户只调用一次#notify_by_email ,我的规范失败了:

1) Event#notify_by_email only sends once per user
     Failure/Error: expect(EventMailer).to receive(:event_added).once
       (<EventMailer (class)>).event_added(any args)
           expected: 1 time with any arguments
           received: 0 times with any arguments

The spec looks like: 规范如下:

let(:owner) { User.make! }
let(:product) { Product.make! }
let(:event) { Task.make!(user: owner, product: product) }

describe '#notify_by_email' do
  before do
    EventMailer.stub(:delay).and_return(EventMailer)
  end

  it 'only sends once per user' do
    event.notify_by_email(owner)
    event.notify_by_email(owner)

    expect(EventMailer).to receive(:event_added).once
  end
end

Any insights into why this spec is failing and how I can fix it? 有关此规范失败的原因以及我如何修复它的任何见解? Strangely, if I put a puts statement inside the block that's passed to EmailLog.send_once , it prints only once, the spec still reports that EventMailer.event_added wasn't called. 奇怪的是,如果我将一个puts语句放在传递给EmailLog.send_once的块中,它只打印一次,规范仍然报告没有调用EventMailer.event_added

Your expectation should be declared before the code you're testing. 您的期望应在您正在测试的代码之前声明。 Using expect(...).to receive(...) basically means "this message should be received between now and the end of this spec". 使用expect(...).to receive(...)基本上意味着“应该在此规范的现在和结束之间接收此消息”。 Because the expectation is the last line of your spec, it fails. 因为期望是您的规范的最后一行,它失败了。

Try moving it before and you should be good to go: 尝试之前移动它,你应该好好去:

it 'only sends once per user' do
  expect(EventMailer).to receive(:event_added).once

  event.notify_by_email(owner)
  event.notify_by_email(owner)
end

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM