ver*_*rus 1 ruby rspec exception
我试图检查我的一个类方法是否响应无效输入有异常,但Rspec没有它.
我的班级文件:
class WhateverClass
def run(options)
if options['input'].nil? || options['input'].empty?
fail ArgumentError, 'No input object provided in configuration.'
end
end
end
Run Code Online (Sandbox Code Playgroud)
我的Rspec测试:
RSpec.describe WhateverClass do
it 'should raise an ArgumentError when provided invalid input' do
invalid_input = { 'nonsense' => 'here' }
expect(WhateverClass.new.run(invalid_input)).to raise_error(ArgumentError)
end
end
Run Code Online (Sandbox Code Playgroud)
运行上述测试的结果如下:
1) WhateverClass should raise an ArgumentError when provided invalid input
Failure/Error: expect(WhateverClass.new.run(invalid_input)).to raise_error(ArgumentError)
ArgumentError:
No input object provided in configuration.
# ./whatever_class.rb:9:in `run'
# ./spec/whatever_class_spec.rb:14:in `block (2 levels) in <top (required)>'
Finished in 0.00048 seconds (files took 1.51 seconds to load)
1 example, 1 failure
Run Code Online (Sandbox Code Playgroud)
================================================== =
请注意,如果我这样做:
RSpec.describe WhateverClass do
it 'should raise an ArgumentError when provided invalid input' do
expect{ fail ArgumentError }.to raise_error(ArgumentError)
invalid_input = { 'nonsense' => 'here' }
expect(WhateverClass.new.run(invalid_input)).to raise_error(ArgumentError)
end
end
Run Code Online (Sandbox Code Playgroud)
第一个期望通过,但第二个预期失败.
如何使此测试正常运行?
事实证明,改变它:
expect(WhateverClass.new.run(invalid_input)).to raise_error(ArgumentError)
Run Code Online (Sandbox Code Playgroud)
至:
expect { WhateverClass.new.run(invalid_input) }.to raise_error(ArgumentError)
Run Code Online (Sandbox Code Playgroud)
解决了这个问题.希望这有助于其他人.
切换到块形式expect是正确的做法,但我认为一些解释是值得的。
当你说:
expect(WhateverClass.new.run(invalid_input)).to ...
Run Code Online (Sandbox Code Playgroud)
你实际上是在说:
x = WhateverClass.new.run(invalid_input)
expect(x).to ...
Run Code Online (Sandbox Code Playgroud)
soWhateverClass.new.run(invalid_input)将expect在构建参数时进行评估(即调用before expect)。这意味着在expect可以做任何事情之前引发异常。
当你说:
expect { WhateverClass.new.run(invalid_input) }.to ...
Run Code Online (Sandbox Code Playgroud)
您正在提供expect一个块 ( { WhateverClass.new.run(invalid_input) }) 并将expect在它设置其异常处理后执行该块。这意味着当expect的异常处理程序就位时将引发异常,因此将捕获异常并执行toonexpect的返回值的方法。