I want to test my method which runs method Temp::Service.run two times inside it:
module Temp
class Service
def self.do_job
# first call step 1
run("step1", {"arg1"=> "v1", "arg2"=>"v2"})
# second call step 2
run("step2", {"arg3"=> "v3"})
end
def self.run(name, p)
# do smth
return true
end
end
end
I want to test arguments provided to second call of method :run with first argument 'step2' while I want to ignore the first call of the same method :run but with first argument 'step1'.
I have the RSpec test
RSpec.describe "My spec", :type => :request do
describe 'method' do
it 'should call' do
# skip this
allow(Temp::Service).to receive(:run).with('step1', anything).and_return(true)
# check this
expect(Temp::Service).to receive(:run) do |name, p|
expect(name).to eq 'step2'
# check p
expect(p['arg3']).not_to be_nil
end
# do the job
Temp::Service.do_job
end
end
end
but I got error
expected: "step2"
got: "step1"
(compared using ==)
How to correctly use allow and expect for the same method ?
Mocking with RSpec is done with the rspec-mocks gem. If you have rspec as a dependency in your Gemfile , you already have rspec-mocks available.
In RSpec, a stub is often called a Method Stub, it's a special type of method that “stands in” for an existing method, or for a method that doesn't even exist yet.
Use the allow method with the receive matcher on a test double or a real. object to tell the object to return a value (or values) in response to a given. message. Nothing happens if the message is never received.
Use let to define a memoized helper method. The value will be cached. across multiple calls in the same example but not across examples. Note that let is lazy-evaluated: it is not evaluated until the first time. the method it defines is invoked.
Seems like you are missing the .with('step2', anything)
it 'should call' do
allow(Temp::Service).to receive(:run).with('step1', anything).and_return(true)
# Append `.with('step2', anything)` here
expect(Temp::Service).to receive(:run).with('step2', anything) do |name, p|
expect(name).to eq 'step2' # you might not need this anymore as it is always gonna be 'step2'
expect(p['arg3']).not_to be_nil
end
Temp::Service.do_job
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