Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Handle keyword arguments separately for and_call_original in supported rubies #1324

Closed
wants to merge 11 commits into from
2 changes: 1 addition & 1 deletion .rubocop_rspec_base.yml
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# This file was generated on 2020-03-30T16:31:25+02:00 from the rspec-dev repo.
# This file was generated on 2020-04-03T18:53:23+03:00 from the rspec-dev repo.
# DO NOT modify it by hand as your changes will get lost the next time it is generated.

# This file contains defaults for RSpec projects. Individual projects
Expand Down
12 changes: 7 additions & 5 deletions .travis.yml
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# This file was generated on 2020-03-30T16:31:25+02:00 from the rspec-dev repo.
# This file was generated on 2020-04-03T18:53:23+03:00 from the rspec-dev repo.
# DO NOT modify it by hand as your changes will get lost the next time it is generated.

# In order to install old Rubies, we need to use old Ubuntu distibution.
Expand All @@ -22,10 +22,10 @@ rvm:
- 2.1
- 2.2.10
- 2.3.8
- 2.4.9
- 2.5.7
- 2.6.5
- 2.7.0
- 2.4.10
- 2.5.8
- 2.6.6
- 2.7.1
- ruby-head
- ree
- rbx-3
Expand All @@ -38,6 +38,8 @@ matrix:
include:
- rvm: jruby-1.7
env: JRUBY_OPTS='--dev --1.8'
- rvm: 2.7.1
env: DIFF_LCS_VERSION='~> 1.3.0'
allow_failures:
- rvm: jruby-head
- rvm: ruby-head
Expand Down
2 changes: 2 additions & 0 deletions Changelog.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,8 @@ Enhancements:
* Add the ability to set a custom error generator in `MessageExpectation`.
This will allow rspec-expectations to inject a custom failure message.
(Benoit Tigeot and Nicolas Zermati, #1312)
* Return the result of the block passed to `RSpec::Mocks.with_temporary_scope`
when block run. (@expeehaa, #1329)

### 3.9.1 / 2019-12-31
[Full Changelog](http://github.com/rspec/rspec-mocks/compare/v3.9.0...v3.9.1)
Expand Down
14 changes: 14 additions & 0 deletions Gemfile
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,20 @@ branch = File.read(File.expand_path("../maintenance-branch", __FILE__)).chomp
end
end

if RUBY_VERSION < '1.9.3'
gem 'rake', '< 11.0.0' # rake 11 requires Ruby 1.9.3 or later
elsif RUBY_VERSION < '2.0.0'
gem 'rake', '< 12.0.0' # rake 12 requires Ruby 2.0.0 or later
else
gem 'rake', '> 12.3.2'
end

if ENV['DIFF_LCS_VERSION']
gem 'diff-lcs', ENV['DIFF_LCS_VERSION']
else
gem 'diff-lcs', '~> 1.4', '>= 1.4.3'
end

gem 'yard', '~> 0.9.24', :require => false

# No need to run rubocop on earlier versions
Expand Down
2 changes: 1 addition & 1 deletion appveyor.yml
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# This file was generated on 2020-03-30T16:31:25+02:00 from the rspec-dev repo.
# This file was generated on 2020-04-03T18:53:23+03:00 from the rspec-dev repo.
# DO NOT modify it by hand as your changes will get lost the next time it is generated.

version: "{build}"
Expand Down
5 changes: 4 additions & 1 deletion lib/rspec/mocks.rb
Original file line number Diff line number Diff line change
Expand Up @@ -87,12 +87,15 @@ def self.expect_message(subject, message, opts={}, &block)

# Call the passed block and verify mocks after it has executed. This allows
# mock usage in arbitrary places, such as a `before(:all)` hook.
#
# @return [Object] the return value from the block
def self.with_temporary_scope
setup

begin
yield
result = yield
verify
result
ensure
teardown
end
Expand Down
21 changes: 20 additions & 1 deletion lib/rspec/mocks/message_expectation.rb
Original file line number Diff line number Diff line change
Expand Up @@ -98,7 +98,7 @@ def and_return(first_value, *values)
# expect(counter.count).to eq(original_count + 1)
def and_call_original
wrap_original(__method__) do |original, *args, &block|
original.call(*args, &block)
__call_original(original, *args, &block)
end
end

Expand Down Expand Up @@ -354,6 +354,25 @@ def to_s
end
alias inspect to_s

private

if RSpec::Support::RubyFeatures.kw_args_supported?
def __call_original(original, *args, &block)
if RSpec::Support::MethodSignature.new(original).has_kw_args_in?(args)
binding.eval(<<-CODE, __FILE__, __LINE__)
benoittgt marked this conversation as resolved.
Show resolved Hide resolved
kwargs = args.pop
original.call(*args, **kwargs, &block)
CODE
else
original.call(*args, &block)
end
end
else
def __call_original(original, *args, &block)
original.call(*args, &block)
end
end

# @private
# Contains the parts of `MessageExpectation` that aren't part of
# rspec-mocks' public API. The class is very big and could really use
Expand Down
2 changes: 1 addition & 1 deletion rspec-mocks.gemspec
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ Gem::Specification.new do |s|

s.add_runtime_dependency "diff-lcs", ">= 1.2.0", "< 2.0"

s.add_development_dependency 'rake', '~> 10.0.0'
s.add_development_dependency 'rake', '> 10.0.0'
s.add_development_dependency 'cucumber', '~> 1.3.15'
s.add_development_dependency 'aruba', '~> 0.14.10'
s.add_development_dependency 'minitest', '~> 5.2'
Expand Down
2 changes: 1 addition & 1 deletion script/clone_all_rspec_repos
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
#!/bin/bash
# This file was generated on 2020-03-30T16:31:25+02:00 from the rspec-dev repo.
# This file was generated on 2020-04-03T18:53:23+03:00 from the rspec-dev repo.
# DO NOT modify it by hand as your changes will get lost the next time it is generated.

set -e
Expand Down
2 changes: 1 addition & 1 deletion script/functions.sh
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# This file was generated on 2020-03-30T16:31:25+02:00 from the rspec-dev repo.
# This file was generated on 2020-04-03T18:53:23+03:00 from the rspec-dev repo.
# DO NOT modify it by hand as your changes will get lost the next time it is generated.

SCRIPT_DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )"
Expand Down
2 changes: 1 addition & 1 deletion script/predicate_functions.sh
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# This file was generated on 2020-03-30T16:31:25+02:00 from the rspec-dev repo.
# This file was generated on 2020-04-03T18:53:23+03:00 from the rspec-dev repo.
# DO NOT modify it by hand as your changes will get lost the next time it is generated.

function is_mri {
Expand Down
2 changes: 1 addition & 1 deletion script/run_build
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
#!/bin/bash
# This file was generated on 2020-03-30T16:31:25+02:00 from the rspec-dev repo.
# This file was generated on 2020-04-03T18:53:23+03:00 from the rspec-dev repo.
# DO NOT modify it by hand as your changes will get lost the next time it is generated.

set -e
Expand Down
2 changes: 1 addition & 1 deletion script/travis_functions.sh
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# This file was generated on 2020-03-30T16:31:25+02:00 from the rspec-dev repo.
# This file was generated on 2020-04-03T18:53:23+03:00 from the rspec-dev repo.
# DO NOT modify it by hand as your changes will get lost the next time it is generated.

# Taken from:
Expand Down
2 changes: 1 addition & 1 deletion script/update_rubygems_and_install_bundler
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
#!/bin/bash
# This file was generated on 2020-03-30T16:31:25+02:00 from the rspec-dev repo.
# This file was generated on 2020-04-03T18:53:23+03:00 from the rspec-dev repo.
# DO NOT modify it by hand as your changes will get lost the next time it is generated.

set -e
Expand Down
31 changes: 31 additions & 0 deletions spec/rspec/mocks/and_call_original_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,19 @@ def meth_2(x)
yield x, :additional_yielded_arg
end

if RSpec::Support::RubyFeatures.kw_args_supported?
binding.eval(<<-CODE, __FILE__, __LINE__)
def meth_3(keyword_arg: nil)
keyword_arg
end

def initialize(initialize_arg: nil)
@initialize_arg = initialize_arg
end
attr_reader :initialize_arg
CODE
end

def self.new_instance
new
end
Expand Down Expand Up @@ -59,6 +72,24 @@ def self.new_instance
expect(value).to eq([:submitted_arg, :additional_yielded_arg])
end

if RSpec::Support::RubyFeatures.kw_args_supported?
it 'works with keyword arguments' do
expect(instance).to receive(:meth_3).and_call_original
binding.eval(<<-CODE, __FILE__, __LINE__)
expect(instance.meth_3(keyword_arg: :original_arg)).to eq :original_arg
CODE
end

it 'works with keyword arguments for .initialize' do
expect(klass).to receive(:new).with(initialize_arg: :initialize_arg)
.and_call_original
binding.eval(<<-CODE, __FILE__, __LINE__)
instance = klass.new(initialize_arg: :initialize_arg)
expect(instance.initialize_arg).to eq :initialize_arg
CODE
end
end

it 'errors when you pass through the wrong number of args' do
expect(instance).to receive(:meth_1).and_call_original
expect(instance).to receive(:meth_2).twice.and_call_original
Expand Down
12 changes: 7 additions & 5 deletions spec/rspec/mocks/diffing_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@
require "pp"

RSpec.describe "Diffs printed when arguments don't match" do
include RSpec::Support::Spec::DiffHelpers

before do
allow(RSpec::Mocks.configuration).to receive(:color?).and_return(false)
end
Expand Down Expand Up @@ -68,7 +70,7 @@
expect(d).to receive(:foo).with(expected_hash)
expect {
d.foo(:bad => :hash)
}.to fail_with(/\A#<Double "double"> received :foo with unexpected arguments\n expected: \(#{hash_regex_inspect expected_hash}\)\n got: \(#{hash_regex_inspect actual_hash}\)\nDiff:\n@@ \-1\,2 \+1\,2 @@\n\-\[#{hash_regex_inspect expected_hash}\]\n\+\[#{hash_regex_inspect actual_hash}\]\n\z/)
}.to fail_with(/\A#<Double "double"> received :foo with unexpected arguments\n expected: \(#{hash_regex_inspect expected_hash}\)\n got: \(#{hash_regex_inspect actual_hash}\)\nDiff:\n@@ #{Regexp.escape one_line_header} @@\n\-\[#{hash_regex_inspect expected_hash}\]\n\+\[#{hash_regex_inspect actual_hash}\]\n\z/)
end
end

Expand Down Expand Up @@ -101,7 +103,7 @@ def hash_regex_inspect(hash)
expect(d).to receive(:foo).with([:a, :b, :c])
expect {
d.foo([])
}.to fail_with("#<Double \"double\"> received :foo with unexpected arguments\n expected: ([:a, :b, :c])\n got: ([])\nDiff:\n@@ -1,2 +1,2 @@\n-[[:a, :b, :c]]\n+[[]]\n")
}.to fail_with("#<Double \"double\"> received :foo with unexpected arguments\n expected: ([:a, :b, :c])\n got: ([])\nDiff:\n@@ #{one_line_header} @@\n-[[:a, :b, :c]]\n+[[]]\n")
end
end

Expand All @@ -117,7 +119,7 @@ def hash_regex_inspect(hash)
d.foo([])
}.to fail_with("#<Double \"double\"> received :foo with unexpected arguments\n" \
" expected: (#{collab_inspect})\n" \
" got: ([])\nDiff:\n@@ -1,2 +1,2 @@\n-[#{collab_inspect}]\n+[[]]\n")
" got: ([])\nDiff:\n@@ #{one_line_header} @@\n-[#{collab_inspect}]\n+[[]]\n")
end
end
end
Expand All @@ -136,7 +138,7 @@ def hash_regex_inspect(hash)
d.foo([:a, :b])
}.to fail_with("#<Double \"double\"> received :foo with unexpected arguments\n" \
" expected: (#{collab_description})\n" \
" got: ([:a, :b])\nDiff:\n@@ -1,2 +1,2 @@\n-[\"#{collab_description}\"]\n+[[:a, :b]]\n")
" got: ([:a, :b])\nDiff:\n@@ #{one_line_header} @@\n-[\"#{collab_description}\"]\n+[[:a, :b]]\n")
end
end
end
Expand Down Expand Up @@ -164,7 +166,7 @@ def inspect
d.foo([:a, :b])
}.to fail_with("#<Double \"double\"> received :foo with unexpected arguments\n" \
" expected: (#{collab_inspect})\n" \
" got: ([:a, :b])\nDiff:\n@@ -1,2 +1,2 @@\n-[#{collab_pp}]\n+[[:a, :b]]\n")
" got: ([:a, :b])\nDiff:\n@@ #{one_line_header} @@\n-[#{collab_pp}]\n+[[:a, :b]]\n")
end
end
end
Expand Down
3 changes: 2 additions & 1 deletion spec/rspec/mocks/formatting_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@

RSpec.describe "Test doubles format well in failure messages" do
include RSpec::Matchers::FailMatchers
include RSpec::Support::Spec::DiffHelpers

RSpec::Matchers.define :format_in_failures_as do |expected|
match do |dbl|
Expand Down Expand Up @@ -101,7 +102,7 @@ def actual_formatting(double)
}.to fail_with(<<-EOS.gsub(/^\s+\|/, ''))
|expected [#<Double "Foo">] to include #<Double "Bar">
|Diff:
|@@ -1,2 +1,2 @@
|@@ #{one_line_header} @@
|-[#<Double "Bar">]
|+[#<Double "Foo">]
EOS
Expand Down
4 changes: 4 additions & 0 deletions spec/rspec/mocks_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -209,6 +209,10 @@
}.to raise_error("boom") # rather than MockExpectationError
end

it 'returns the result of the passed block' do
expect(RSpec::Mocks.with_temporary_scope { 5 }).to eq 5
end

def capture_error
yield
rescue Exception => @error
Expand Down