I have a Mailer
that looks something like this:
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:
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. .delay
is added by Sidekiq.
But when I try to test that #notify_by_email
is called only once per event and user, my spec fails:
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.
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". 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
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With