您当前发布的代码存在一些语法问题(见下文);然而,你正在寻找的是
Verifying Double
在这种情况下,a
instance_double
.
来自文件(着重部分为后加):
一
instance_double
是最常见的双重验证类型。它将类名或对象作为第一个参数,然后验证任何被存根的方法是否存在于
例子
那个班。此外当它接收消息时,
它验证所提供的参数是否得到方法签名的支持,包括arity和允许或必需的关键字参数(如果有的话)
.
例如,如果您更改
foo = double(Foo)
到
foo = instance_double(Foo)
您的原始测试将通过,当您将方法更改为
def do_thing(arg_one_hundred:, arg_two:)
它将会失败。
代码当前存在的问题:
-
Bar#initialize
不接受任何这样的论点
described_class.new(mock_foo)
将引发错误。我不确定是否应该将争论视为依赖注入,因此在这里提出正确的解决方案更加困难。
-
to_receive
不是一种方法
allow(foo).to_receive(:do_thing)
将引发错误
-
expect(...).to recieve
但是,由于您已经调用了,因此设置了对象的期望值
subject.do_delegated_thing
在设置期望之前,期望总是会失败(在方法调用之前移动期望)
Working Example
:(有明显修改)
class Foo
def do_thing(arg_one:, arg_two:); end
end
class Baz
def do_thing(arg_one_hundred:, arg_two:); end
end
class Bar
def initialize
@foo = Foo.new
end
def do_delegated_thing
foo.do_thing(arg_one: "x", arg_two: "y")
end
private
attr_reader :foo
end
describe Bar do
let(:mock_foo) {instance_double(Foo, do_thing: nil)}
let(:mock_baz) {double(Baz, do_thing: nil)}
let(:mock_baz_2) {instance_double(Baz, do_thing: nil)}
let(:subject) { described_class.new }
it "calls Foo with expected arguments" do
allow(subject).to receive(:foo).and_return(mock_foo)
expect(mock_foo).to receive(:do_thing).with(arg_one: "x", arg_two: "y")
subject.do_delegated_thing
end
context 'comparing double and instance_double' do
it "calls double with unexpected arguments" do
allow(subject).to receive(:foo).and_return(mock_baz)
expect(mock_baz).to receive(:do_thing).with(arg_one: "x", arg_two: "y")
subject.do_delegated_thing
end
it "calls instance_double with unexpected arguments" do
allow(subject).to receive(:foo).and_return(mock_baz_2)
expect(mock_baz_2).to receive(:do_thing).with(arg_one: "x", arg_two: "y")
subject.do_delegated_thing
end
end
end
输出:
Bar
calls Foo with expected arguments
comparing double and instance_double
calls double with unexpected arguments
calls instance_double with unexpected arguments (FAILED - 1)
Failures:
1) Bar comparing double and instance_double calls instance_double with unexpected arguments
Failure/Error: expect(mock_baz_2).to receive(:do_thing).with(arg_one: "x", arg_two: "y")
Missing required keyword arguments: arg_one_hundred
Finished in 0.00752 seconds (files took 0.0997 seconds to load)
3 examples, 1 failure