Home > Mobile >  Rails test job and raise errors if any
Rails test job and raise errors if any

Time:10-13

I have a job, which I'm currently testing using RSpec:

# app/jobs/do_something_job.rb
class DoSomethingJob < ApplicationJob
  def perform(a, b, c)
    Service.new(a, b, c).call
  end
end

The example file looks this way:

require 'spec_helper'

describe DoSomethingJob do
  it do
    expect { described_class.perform_later(a, b, c) }.to have_enqueued_job
  end
end

That example certainly succeeds, it queues the job no matter what happens within the perform method body.

Now if I update the Service class, like removing an argument on its initialize method, leaving this way:

class Service
  def initialize(a, b)
    ...
  end
end

And I don't update the job example, it'll anyway succeed because the job is enqueued. What I'm trying to do is to test the body of DoSomethingJob#perform executes without errors, without getting on the specifics of Service itself (it has its own tests).

I tried mocking Service and using expect { ... }.not_to raise_error, but that fakes the test, since I have to stub the new and call methods it receives.

Is there a way to achieve this?

CodePudding user response:

First create a class method on the service so that you don't have to stub an instance:

class Service
  def self.call(a, b, c)
     new(a, b, c).call
  end
end

# app/jobs/do_something_job.rb
class DoSomethingJob < ApplicationJob
  def perform(a, b, c)
    Service.call(a, b, c)
  end
end

Then simply place an expectation on what you want the method to do (in this case call the collaborator) and perform the job immediately:

describe DoSomethingJob do
  it "calls Service with a, b, c" do
    expect(Service).to receive(:call).with(1, 2, 3).and_call_original
    DoSomethingJob.perform_now(1, 2, 3)
  end
end
  • Related