rspec-mocks 2.13.1 → 2.14.0.rc1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/Changelog.md +45 -4
- data/README.md +1 -1
- data/features/argument_matchers/README.md +2 -2
- data/features/argument_matchers/explicit.feature +2 -3
- data/features/argument_matchers/general_matchers.feature +2 -2
- data/features/argument_matchers/type_matchers.feature +3 -4
- data/features/message_expectations/README.md +2 -2
- data/features/message_expectations/any_instance.feature +2 -2
- data/features/message_expectations/block_local_expectations.feature.pending +3 -3
- data/features/message_expectations/expect_message_using_expect.feature +103 -0
- data/features/message_expectations/expect_message_using_should_receive.feature +118 -0
- data/features/message_expectations/receive_counts.feature +1 -1
- data/features/method_stubs/README.md +1 -1
- data/features/method_stubs/any_instance.feature +11 -11
- data/features/method_stubs/as_null_object.feature +1 -1
- data/features/method_stubs/stub_implementation.feature +2 -2
- data/features/outside_rspec/configuration.feature +0 -20
- data/features/spies/spy_partial_mock_method.feature +34 -0
- data/features/spies/spy_pure_mock_method.feature +76 -0
- data/features/spies/spy_unstubbed_method.feature +18 -0
- data/features/step_definitions/additional_cli_steps.rb +7 -0
- data/features/test_frameworks/test_unit.feature +43 -0
- data/lib/rspec/mocks.rb +9 -34
- data/lib/rspec/mocks/any_instance/chain.rb +8 -2
- data/lib/rspec/mocks/any_instance/expectation_chain.rb +19 -16
- data/lib/rspec/mocks/any_instance/recorder.rb +6 -3
- data/lib/rspec/mocks/any_instance/stub_chain.rb +11 -11
- data/lib/rspec/mocks/any_instance/stub_chain_chain.rb +8 -10
- data/lib/rspec/mocks/argument_list_matcher.rb +7 -3
- data/lib/rspec/mocks/configuration.rb +28 -1
- data/lib/rspec/mocks/deprecation.rb +18 -0
- data/lib/rspec/mocks/error_generator.rb +60 -8
- data/lib/rspec/mocks/errors.rb +1 -1
- data/lib/rspec/mocks/example_methods.rb +39 -3
- data/lib/rspec/mocks/extensions/marshal.rb +4 -10
- data/lib/rspec/mocks/framework.rb +16 -4
- data/lib/rspec/mocks/instance_method_stasher.rb +3 -0
- data/lib/rspec/mocks/matchers/have_received.rb +93 -0
- data/lib/rspec/mocks/matchers/receive.rb +92 -0
- data/lib/rspec/mocks/message_expectation.rb +66 -129
- data/lib/rspec/mocks/method_double.rb +50 -43
- data/lib/rspec/mocks/mutate_const.rb +8 -20
- data/lib/rspec/mocks/proxy.rb +41 -25
- data/lib/rspec/mocks/proxy_for_nil.rb +36 -0
- data/lib/rspec/mocks/space.rb +64 -11
- data/lib/rspec/mocks/stub_chain.rb +51 -0
- data/lib/rspec/mocks/syntax.rb +329 -0
- data/lib/rspec/mocks/targets.rb +69 -0
- data/lib/rspec/mocks/test_double.rb +25 -4
- data/lib/rspec/mocks/version.rb +1 -1
- data/lib/spec/mocks.rb +1 -3
- data/spec/rspec/mocks/and_call_original_spec.rb +8 -0
- data/spec/rspec/mocks/and_yield_spec.rb +6 -6
- data/spec/rspec/mocks/any_instance_spec.rb +43 -31
- data/spec/rspec/mocks/any_number_of_times_spec.rb +6 -0
- data/spec/rspec/mocks/argument_expectation_spec.rb +12 -14
- data/spec/rspec/mocks/at_least_spec.rb +46 -37
- data/spec/rspec/mocks/at_most_spec.rb +12 -12
- data/spec/rspec/mocks/block_return_value_spec.rb +18 -1
- data/spec/rspec/mocks/bug_report_10260_spec.rb +1 -1
- data/spec/rspec/mocks/bug_report_10263_spec.rb +1 -1
- data/spec/rspec/mocks/bug_report_11545_spec.rb +4 -4
- data/spec/rspec/mocks/bug_report_600_spec.rb +1 -1
- data/spec/rspec/mocks/bug_report_7611_spec.rb +1 -1
- data/spec/rspec/mocks/configuration_spec.rb +124 -0
- data/spec/rspec/mocks/double_spec.rb +13 -1
- data/spec/rspec/mocks/failing_argument_matchers_spec.rb +17 -1
- data/spec/rspec/mocks/hash_excluding_matcher_spec.rb +13 -13
- data/spec/rspec/mocks/matchers/have_received_spec.rb +266 -0
- data/spec/rspec/mocks/matchers/receive_spec.rb +318 -0
- data/spec/rspec/mocks/methods_spec.rb +27 -0
- data/spec/rspec/mocks/mock_ordering_spec.rb +4 -4
- data/spec/rspec/mocks/mock_space_spec.rb +94 -39
- data/spec/rspec/mocks/mock_spec.rb +65 -50
- data/spec/rspec/mocks/multiple_return_value_spec.rb +10 -10
- data/spec/rspec/mocks/mutate_const_spec.rb +21 -1
- data/spec/rspec/mocks/nil_expectation_warning_spec.rb +10 -4
- data/spec/rspec/mocks/null_object_mock_spec.rb +11 -2
- data/spec/rspec/mocks/once_counts_spec.rb +5 -5
- data/spec/rspec/mocks/options_hash_spec.rb +4 -4
- data/spec/rspec/mocks/partial_mock_spec.rb +20 -11
- data/spec/rspec/mocks/partial_mock_using_mocks_directly_spec.rb +7 -7
- data/spec/rspec/mocks/passing_argument_matchers_spec.rb +2 -2
- data/spec/rspec/mocks/precise_counts_spec.rb +6 -6
- data/spec/rspec/mocks/serialization_spec.rb +1 -22
- data/spec/rspec/mocks/stash_spec.rb +4 -12
- data/spec/rspec/mocks/stub_implementation_spec.rb +3 -3
- data/spec/rspec/mocks/stub_spec.rb +44 -20
- data/spec/rspec/mocks/stubbed_message_expectations_spec.rb +6 -6
- data/spec/rspec/mocks/twice_counts_spec.rb +6 -6
- data/spec/rspec/mocks_spec.rb +1 -3
- data/spec/spec_helper.rb +25 -1
- metadata +86 -81
- data/features/message_expectations/expect_message.feature +0 -94
- data/lib/rspec/mocks/any_instance.rb +0 -81
- data/lib/rspec/mocks/extensions/psych.rb +0 -23
- data/lib/rspec/mocks/methods.rb +0 -155
- data/lib/rspec/mocks/serialization.rb +0 -34
- data/spec/rspec/mocks/combining_implementation_instructions_spec.rb +0 -197
@@ -1,94 +0,0 @@
|
|
1
|
-
Feature: expect a message
|
2
|
-
|
3
|
-
Use should_receive() to set an expectation that a receiver should receive a
|
4
|
-
message before the example is completed.
|
5
|
-
|
6
|
-
Scenario: expect a message
|
7
|
-
Given a file named "spec/account_spec.rb" with:
|
8
|
-
"""ruby
|
9
|
-
require "account"
|
10
|
-
|
11
|
-
describe Account do
|
12
|
-
context "when closed" do
|
13
|
-
it "logs an account closed message" do
|
14
|
-
logger = double("logger")
|
15
|
-
account = Account.new
|
16
|
-
account.logger = logger
|
17
|
-
|
18
|
-
logger.should_receive(:account_closed)
|
19
|
-
|
20
|
-
account.close
|
21
|
-
end
|
22
|
-
end
|
23
|
-
end
|
24
|
-
"""
|
25
|
-
And a file named "lib/account.rb" with:
|
26
|
-
"""ruby
|
27
|
-
class Account
|
28
|
-
attr_accessor :logger
|
29
|
-
|
30
|
-
def close
|
31
|
-
logger.account_closed
|
32
|
-
end
|
33
|
-
end
|
34
|
-
"""
|
35
|
-
When I run `rspec spec/account_spec.rb`
|
36
|
-
Then the output should contain "1 example, 0 failures"
|
37
|
-
|
38
|
-
Scenario: expect a message with an argument
|
39
|
-
Given a file named "spec/account_spec.rb" with:
|
40
|
-
"""ruby
|
41
|
-
require "account"
|
42
|
-
|
43
|
-
describe Account do
|
44
|
-
context "when closed" do
|
45
|
-
it "logs an account closed message" do
|
46
|
-
logger = double("logger")
|
47
|
-
account = Account.new
|
48
|
-
account.logger = logger
|
49
|
-
|
50
|
-
logger.should_receive(:account_closed).with(account)
|
51
|
-
|
52
|
-
account.close
|
53
|
-
end
|
54
|
-
end
|
55
|
-
end
|
56
|
-
"""
|
57
|
-
And a file named "lib/account.rb" with:
|
58
|
-
"""ruby
|
59
|
-
class Account
|
60
|
-
attr_accessor :logger
|
61
|
-
|
62
|
-
def close
|
63
|
-
logger.account_closed(self)
|
64
|
-
end
|
65
|
-
end
|
66
|
-
"""
|
67
|
-
When I run `rspec spec/account_spec.rb`
|
68
|
-
Then the output should contain "1 example, 0 failures"
|
69
|
-
|
70
|
-
Scenario: provide a return value
|
71
|
-
Given a file named "message_expectation_spec.rb" with:
|
72
|
-
"""ruby
|
73
|
-
describe "a message expectation" do
|
74
|
-
context "with a return value" do
|
75
|
-
context "specified in a block" do
|
76
|
-
it "returns the specified value" do
|
77
|
-
receiver = double("receiver")
|
78
|
-
receiver.should_receive(:message) { :return_value }
|
79
|
-
receiver.message.should eq(:return_value)
|
80
|
-
end
|
81
|
-
end
|
82
|
-
|
83
|
-
context "specified with and_return" do
|
84
|
-
it "returns the specified value" do
|
85
|
-
receiver = double("receiver")
|
86
|
-
receiver.should_receive(:message).and_return(:return_value)
|
87
|
-
receiver.message.should eq(:return_value)
|
88
|
-
end
|
89
|
-
end
|
90
|
-
end
|
91
|
-
end
|
92
|
-
"""
|
93
|
-
When I run `rspec message_expectation_spec.rb`
|
94
|
-
Then the output should contain "2 examples, 0 failures"
|
@@ -1,81 +0,0 @@
|
|
1
|
-
require 'rspec/mocks/any_instance/chain'
|
2
|
-
require 'rspec/mocks/any_instance/stub_chain'
|
3
|
-
require 'rspec/mocks/any_instance/stub_chain_chain'
|
4
|
-
require 'rspec/mocks/any_instance/expectation_chain'
|
5
|
-
require 'rspec/mocks/any_instance/message_chains'
|
6
|
-
require 'rspec/mocks/any_instance/recorder'
|
7
|
-
|
8
|
-
module RSpec
|
9
|
-
module Mocks
|
10
|
-
module AnyInstance
|
11
|
-
# Used to set stubs and message expectations on any instance of a given
|
12
|
-
# class. Returns a [Recorder](Recorder), which records messages like
|
13
|
-
# `stub` and `should_receive` for later playback on instances of the
|
14
|
-
# class.
|
15
|
-
#
|
16
|
-
# @example
|
17
|
-
#
|
18
|
-
# Car.any_instance.should_receive(:go)
|
19
|
-
# race = Race.new
|
20
|
-
# race.cars << Car.new
|
21
|
-
# race.go # assuming this delegates to all of its cars
|
22
|
-
# # this example would pass
|
23
|
-
#
|
24
|
-
# Account.any_instance.stub(:balance) { Money.new(:USD, 25) }
|
25
|
-
# Account.new.balance # => Money.new(:USD, 25))
|
26
|
-
#
|
27
|
-
# @return [Recorder]
|
28
|
-
def any_instance
|
29
|
-
RSpec::Mocks::space.add(self)
|
30
|
-
modify_dup_to_remove_mock_proxy_when_invoked
|
31
|
-
__recorder
|
32
|
-
end
|
33
|
-
|
34
|
-
# @private
|
35
|
-
def rspec_verify
|
36
|
-
__recorder.verify
|
37
|
-
super
|
38
|
-
ensure
|
39
|
-
__recorder.stop_all_observation!
|
40
|
-
restore_dup
|
41
|
-
@__recorder = nil
|
42
|
-
end
|
43
|
-
|
44
|
-
# @private
|
45
|
-
def rspec_reset
|
46
|
-
restore_dup
|
47
|
-
__mock_proxy.reset
|
48
|
-
end
|
49
|
-
|
50
|
-
# @private
|
51
|
-
def __recorder
|
52
|
-
@__recorder ||= AnyInstance::Recorder.new(self)
|
53
|
-
end
|
54
|
-
|
55
|
-
private
|
56
|
-
def modify_dup_to_remove_mock_proxy_when_invoked
|
57
|
-
if method_defined?(:dup) and !method_defined?(:__rspec_original_dup)
|
58
|
-
class_eval do
|
59
|
-
def __rspec_dup(*arguments, &block)
|
60
|
-
__remove_mock_proxy
|
61
|
-
__rspec_original_dup(*arguments, &block)
|
62
|
-
end
|
63
|
-
|
64
|
-
alias_method :__rspec_original_dup, :dup
|
65
|
-
alias_method :dup, :__rspec_dup
|
66
|
-
end
|
67
|
-
end
|
68
|
-
end
|
69
|
-
|
70
|
-
def restore_dup
|
71
|
-
if method_defined?(:__rspec_original_dup)
|
72
|
-
class_eval do
|
73
|
-
alias_method :dup, :__rspec_original_dup
|
74
|
-
remove_method :__rspec_original_dup
|
75
|
-
remove_method :__rspec_dup
|
76
|
-
end
|
77
|
-
end
|
78
|
-
end
|
79
|
-
end
|
80
|
-
end
|
81
|
-
end
|
@@ -1,23 +0,0 @@
|
|
1
|
-
if defined?(Psych) && Psych.respond_to?(:dump)
|
2
|
-
module Psych
|
3
|
-
class << self
|
4
|
-
def dump_with_mocks(object, *args)
|
5
|
-
return dump_without_mocks(object, *args) unless object.instance_variable_defined?(:@mock_proxy)
|
6
|
-
|
7
|
-
mp = object.instance_variable_get(:@mock_proxy)
|
8
|
-
return dump_without_mocks(object, *args) unless mp.is_a?(::RSpec::Mocks::Proxy)
|
9
|
-
|
10
|
-
object.__send__(:remove_instance_variable, :@mock_proxy)
|
11
|
-
|
12
|
-
begin
|
13
|
-
dump_without_mocks(object, *args)
|
14
|
-
ensure
|
15
|
-
object.instance_variable_set(:@mock_proxy, mp)
|
16
|
-
end
|
17
|
-
end
|
18
|
-
|
19
|
-
alias_method :dump_without_mocks, :dump
|
20
|
-
alias_method :dump, :dump_with_mocks
|
21
|
-
end
|
22
|
-
end
|
23
|
-
end
|
data/lib/rspec/mocks/methods.rb
DELETED
@@ -1,155 +0,0 @@
|
|
1
|
-
module RSpec
|
2
|
-
module Mocks
|
3
|
-
# Methods that are added to every object.
|
4
|
-
module Methods
|
5
|
-
# Sets and expectation that this object should receive a message before
|
6
|
-
# the end of the example.
|
7
|
-
#
|
8
|
-
# @example
|
9
|
-
#
|
10
|
-
# logger = double('logger')
|
11
|
-
# thing_that_logs = ThingThatLogs.new(logger)
|
12
|
-
# logger.should_receive(:log)
|
13
|
-
# thing_that_logs.do_something_that_logs_a_message
|
14
|
-
def should_receive(message, opts={}, &block)
|
15
|
-
__mock_proxy.add_message_expectation(opts[:expected_from] || caller(1)[0], message.to_sym, opts, &block)
|
16
|
-
end
|
17
|
-
|
18
|
-
# Sets and expectation that this object should _not_ receive a message
|
19
|
-
# during this example.
|
20
|
-
def should_not_receive(message, &block)
|
21
|
-
__mock_proxy.add_negative_message_expectation(caller(1)[0], message.to_sym, &block)
|
22
|
-
end
|
23
|
-
|
24
|
-
# Tells the object to respond to the message with the specified value.
|
25
|
-
#
|
26
|
-
# @example
|
27
|
-
#
|
28
|
-
# counter.stub(:count).and_return(37)
|
29
|
-
# counter.stub(:count => 37)
|
30
|
-
# counter.stub(:count) { 37 }
|
31
|
-
def stub(message_or_hash, opts={}, &block)
|
32
|
-
if Hash === message_or_hash
|
33
|
-
message_or_hash.each {|message, value| stub(message).and_return value }
|
34
|
-
else
|
35
|
-
__mock_proxy.add_stub(caller(1)[0], message_or_hash.to_sym, opts, &block)
|
36
|
-
end
|
37
|
-
end
|
38
|
-
|
39
|
-
# Removes a stub. On a double, the object will no longer respond to
|
40
|
-
# `message`. On a real object, the original method (if it exists) is
|
41
|
-
# restored.
|
42
|
-
#
|
43
|
-
# This is rarely used, but can be useful when a stub is set up during a
|
44
|
-
# shared `before` hook for the common case, but you want to replace it
|
45
|
-
# for a special case.
|
46
|
-
def unstub(message)
|
47
|
-
__mock_proxy.remove_stub(message)
|
48
|
-
end
|
49
|
-
|
50
|
-
alias_method :stub!, :stub
|
51
|
-
alias_method :unstub!, :unstub
|
52
|
-
|
53
|
-
# @overload stub_chain(method1, method2)
|
54
|
-
# @overload stub_chain("method1.method2")
|
55
|
-
# @overload stub_chain(method1, method_to_value_hash)
|
56
|
-
#
|
57
|
-
# Stubs a chain of methods.
|
58
|
-
#
|
59
|
-
# ## Warning:
|
60
|
-
#
|
61
|
-
# Chains can be arbitrarily long, which makes it quite painless to
|
62
|
-
# violate the Law of Demeter in violent ways, so you should consider any
|
63
|
-
# use of `stub_chain` a code smell. Even though not all code smells
|
64
|
-
# indicate real problems (think fluent interfaces), `stub_chain` still
|
65
|
-
# results in brittle examples. For example, if you write
|
66
|
-
# `foo.stub_chain(:bar, :baz => 37)` in a spec and then the
|
67
|
-
# implementation calls `foo.baz.bar`, the stub will not work.
|
68
|
-
#
|
69
|
-
# @example
|
70
|
-
#
|
71
|
-
# double.stub_chain("foo.bar") { :baz }
|
72
|
-
# double.stub_chain(:foo, :bar => :baz)
|
73
|
-
# double.stub_chain(:foo, :bar) { :baz }
|
74
|
-
#
|
75
|
-
# # Given any of ^^ these three forms ^^:
|
76
|
-
# double.foo.bar # => :baz
|
77
|
-
#
|
78
|
-
# # Common use in Rails/ActiveRecord:
|
79
|
-
# Article.stub_chain("recent.published") { [Article.new] }
|
80
|
-
def stub_chain(*chain, &blk)
|
81
|
-
chain, blk = format_chain(*chain, &blk)
|
82
|
-
if chain.length > 1
|
83
|
-
if matching_stub = __mock_proxy.__send__(:find_matching_method_stub, chain[0].to_sym)
|
84
|
-
chain.shift
|
85
|
-
matching_stub.invoke(nil).stub_chain(*chain, &blk)
|
86
|
-
else
|
87
|
-
next_in_chain = Mock.new
|
88
|
-
stub(chain.shift) { next_in_chain }
|
89
|
-
next_in_chain.stub_chain(*chain, &blk)
|
90
|
-
end
|
91
|
-
else
|
92
|
-
stub(chain.shift, &blk)
|
93
|
-
end
|
94
|
-
end
|
95
|
-
|
96
|
-
# Tells the object to respond to all messages. If specific stub values
|
97
|
-
# are declared, they'll work as expected. If not, the receiver is
|
98
|
-
# returned.
|
99
|
-
def as_null_object
|
100
|
-
@_null_object = true
|
101
|
-
__mock_proxy.as_null_object
|
102
|
-
end
|
103
|
-
|
104
|
-
# Returns true if this object has received `as_null_object`
|
105
|
-
def null_object?
|
106
|
-
defined?(@_null_object)
|
107
|
-
end
|
108
|
-
|
109
|
-
# @private
|
110
|
-
def received_message?(message, *args, &block)
|
111
|
-
__mock_proxy.received_message?(message, *args, &block)
|
112
|
-
end
|
113
|
-
|
114
|
-
# @private
|
115
|
-
def rspec_verify
|
116
|
-
__mock_proxy.verify
|
117
|
-
end
|
118
|
-
|
119
|
-
# @private
|
120
|
-
def rspec_reset
|
121
|
-
__mock_proxy.reset
|
122
|
-
end
|
123
|
-
|
124
|
-
private
|
125
|
-
|
126
|
-
def __mock_proxy
|
127
|
-
@mock_proxy ||= begin
|
128
|
-
mp = if TestDouble === self
|
129
|
-
Proxy.new(self, @name, @options)
|
130
|
-
else
|
131
|
-
Proxy.new(self)
|
132
|
-
end
|
133
|
-
|
134
|
-
Serialization.fix_for(self)
|
135
|
-
mp
|
136
|
-
end
|
137
|
-
end
|
138
|
-
|
139
|
-
def __remove_mock_proxy
|
140
|
-
@mock_proxy = nil
|
141
|
-
end
|
142
|
-
|
143
|
-
def format_chain(*chain, &blk)
|
144
|
-
if Hash === chain.last
|
145
|
-
hash = chain.pop
|
146
|
-
hash.each do |k,v|
|
147
|
-
chain << k
|
148
|
-
blk = lambda { v }
|
149
|
-
end
|
150
|
-
end
|
151
|
-
return chain.join('.').split('.'), blk
|
152
|
-
end
|
153
|
-
end
|
154
|
-
end
|
155
|
-
end
|
@@ -1,34 +0,0 @@
|
|
1
|
-
require 'rspec/mocks/extensions/marshal'
|
2
|
-
require 'rspec/mocks/extensions/psych' if defined?(::Psych)
|
3
|
-
|
4
|
-
module RSpec
|
5
|
-
module Mocks
|
6
|
-
# @private
|
7
|
-
module Serialization
|
8
|
-
# @private
|
9
|
-
def self.fix_for(object)
|
10
|
-
object.extend(YAML) if defined?(::YAML)
|
11
|
-
rescue TypeError
|
12
|
-
# Can't extend Fixnums, Symbols, true, false, or nil
|
13
|
-
end
|
14
|
-
|
15
|
-
# @private
|
16
|
-
module YAML
|
17
|
-
# @private
|
18
|
-
def to_yaml(options = {})
|
19
|
-
return nil if defined?(::Psych) && options.respond_to?(:[]) && options[:nodump]
|
20
|
-
return super(options) unless instance_variable_defined?(:@mock_proxy)
|
21
|
-
|
22
|
-
mp = @mock_proxy
|
23
|
-
remove_instance_variable(:@mock_proxy)
|
24
|
-
|
25
|
-
begin
|
26
|
-
super(options)
|
27
|
-
ensure
|
28
|
-
@mock_proxy = mp
|
29
|
-
end
|
30
|
-
end
|
31
|
-
end
|
32
|
-
end
|
33
|
-
end
|
34
|
-
end
|
@@ -1,197 +0,0 @@
|
|
1
|
-
require 'spec_helper'
|
2
|
-
|
3
|
-
module RSpec
|
4
|
-
module Mocks
|
5
|
-
describe "Combining implementation instructions" do
|
6
|
-
it 'can combine and_yield and and_return' do
|
7
|
-
dbl = double
|
8
|
-
dbl.stub(:foo).and_yield(5).and_return(3)
|
9
|
-
|
10
|
-
expect { |b|
|
11
|
-
expect(dbl.foo(&b)).to eq(3)
|
12
|
-
}.to yield_with_args(5)
|
13
|
-
end
|
14
|
-
|
15
|
-
describe "combining and_yield, a block implementation and and_return" do
|
16
|
-
def verify_combined_implementation
|
17
|
-
dbl = double
|
18
|
-
(yield dbl).and_yield(5).and_return(3)
|
19
|
-
|
20
|
-
expect { |b|
|
21
|
-
expect(dbl.foo(:arg, &b)).to eq(3)
|
22
|
-
}.to yield_with_args(5)
|
23
|
-
|
24
|
-
expect(@block_called).to be_true
|
25
|
-
end
|
26
|
-
|
27
|
-
it 'works when passing a block to `stub`' do
|
28
|
-
verify_combined_implementation do |dbl|
|
29
|
-
dbl.stub(:foo) { @block_called = true }
|
30
|
-
end
|
31
|
-
end
|
32
|
-
|
33
|
-
it 'works when passing a block to `with`' do
|
34
|
-
verify_combined_implementation do |dbl|
|
35
|
-
dbl.stub(:foo).with(:arg) { @block_called = true }
|
36
|
-
end
|
37
|
-
end
|
38
|
-
|
39
|
-
it 'works when passing a block to `exactly`' do
|
40
|
-
verify_combined_implementation do |dbl|
|
41
|
-
dbl.should_receive(:foo).exactly(:once) { @block_called = true }
|
42
|
-
end
|
43
|
-
end
|
44
|
-
|
45
|
-
it 'works when passing a block to `at_least`' do
|
46
|
-
verify_combined_implementation do |dbl|
|
47
|
-
dbl.should_receive(:foo).at_least(:once) { @block_called = true }
|
48
|
-
end
|
49
|
-
end
|
50
|
-
|
51
|
-
it 'works when passing a block to `at_most`' do
|
52
|
-
verify_combined_implementation do |dbl|
|
53
|
-
dbl.should_receive(:foo).at_most(:once) { @block_called = true }
|
54
|
-
end
|
55
|
-
end
|
56
|
-
|
57
|
-
it 'works when passing a block to `times`' do
|
58
|
-
verify_combined_implementation do |dbl|
|
59
|
-
dbl.should_receive(:foo).exactly(1).times { @block_called = true }
|
60
|
-
end
|
61
|
-
end
|
62
|
-
|
63
|
-
it 'works when passing a block to `any_number_of_times`' do
|
64
|
-
verify_combined_implementation do |dbl|
|
65
|
-
dbl.should_receive(:foo).any_number_of_times { @block_called = true }
|
66
|
-
end
|
67
|
-
end
|
68
|
-
|
69
|
-
it 'works when passing a block to `once`' do
|
70
|
-
verify_combined_implementation do |dbl|
|
71
|
-
dbl.should_receive(:foo).once { @block_called = true }
|
72
|
-
end
|
73
|
-
end
|
74
|
-
|
75
|
-
it 'works when passing a block to `twice`' do
|
76
|
-
the_double = nil
|
77
|
-
|
78
|
-
verify_combined_implementation do |dbl|
|
79
|
-
the_double = dbl
|
80
|
-
dbl.should_receive(:foo).twice { @block_called = true }
|
81
|
-
end
|
82
|
-
|
83
|
-
the_double.foo { |a| } # to ensure it is called twice
|
84
|
-
end
|
85
|
-
|
86
|
-
it 'works when passing a block to `ordered`' do
|
87
|
-
verify_combined_implementation do |dbl|
|
88
|
-
dbl.should_receive(:foo).ordered { @block_called = true }
|
89
|
-
end
|
90
|
-
end
|
91
|
-
end
|
92
|
-
|
93
|
-
it 'can combine and_yield and and_return with a block' do
|
94
|
-
dbl = double
|
95
|
-
dbl.stub(:foo).and_yield(5).and_return { :return }
|
96
|
-
|
97
|
-
expect { |b|
|
98
|
-
expect(dbl.foo(&b)).to eq(:return)
|
99
|
-
}.to yield_with_args(5)
|
100
|
-
end
|
101
|
-
|
102
|
-
it 'can combine and_yield and and_raise' do
|
103
|
-
dbl = double
|
104
|
-
dbl.stub(:foo).and_yield(5).and_raise("boom")
|
105
|
-
|
106
|
-
expect { |b|
|
107
|
-
expect { dbl.foo(&b) }.to raise_error("boom")
|
108
|
-
}.to yield_with_args(5)
|
109
|
-
end
|
110
|
-
|
111
|
-
it 'can combine and_yield, a block implementation and and_raise' do
|
112
|
-
dbl = double
|
113
|
-
block_called = false
|
114
|
-
dbl.stub(:foo) { block_called = true }.and_yield(5).and_raise("boom")
|
115
|
-
|
116
|
-
expect { |b|
|
117
|
-
expect { dbl.foo(&b) }.to raise_error("boom")
|
118
|
-
}.to yield_with_args(5)
|
119
|
-
|
120
|
-
expect(block_called).to be_true
|
121
|
-
end
|
122
|
-
|
123
|
-
it 'can combine and_yield and and_throw' do
|
124
|
-
dbl = double
|
125
|
-
dbl.stub(:foo).and_yield(5).and_throw(:bar)
|
126
|
-
|
127
|
-
expect { |b|
|
128
|
-
expect { dbl.foo(&b) }.to throw_symbol(:bar)
|
129
|
-
}.to yield_with_args(5)
|
130
|
-
end
|
131
|
-
|
132
|
-
it 'can combine and_yield, a block implementation and and_throw' do
|
133
|
-
dbl = double
|
134
|
-
block_called = false
|
135
|
-
dbl.stub(:foo) { block_called = true }.and_yield(5).and_throw(:bar)
|
136
|
-
|
137
|
-
expect { |b|
|
138
|
-
expect { dbl.foo(&b) }.to throw_symbol(:bar)
|
139
|
-
}.to yield_with_args(5)
|
140
|
-
|
141
|
-
expect(block_called).to be_true
|
142
|
-
end
|
143
|
-
|
144
|
-
it 'returns `nil` from all terminal actions to discourage further configuration' do
|
145
|
-
expect(double.stub(:foo).and_return(1)).to be_nil
|
146
|
-
expect(double.stub(:foo).and_raise("boom")).to be_nil
|
147
|
-
expect(double.stub(:foo).and_throw(:foo)).to be_nil
|
148
|
-
end
|
149
|
-
|
150
|
-
it 'allows the terminal action to be overriden' do
|
151
|
-
dbl = double
|
152
|
-
stubbed_double = dbl.stub(:foo)
|
153
|
-
|
154
|
-
stubbed_double.and_return(1)
|
155
|
-
expect(dbl.foo).to eq(1)
|
156
|
-
|
157
|
-
stubbed_double.and_return(3)
|
158
|
-
expect(dbl.foo).to eq(3)
|
159
|
-
|
160
|
-
stubbed_double.and_raise("boom")
|
161
|
-
expect { dbl.foo }.to raise_error("boom")
|
162
|
-
|
163
|
-
stubbed_double.and_throw(:bar)
|
164
|
-
expect { dbl.foo }.to throw_symbol(:bar)
|
165
|
-
end
|
166
|
-
|
167
|
-
it 'allows the inner implementation block to be overriden' do
|
168
|
-
dbl = double
|
169
|
-
stubbed_double = dbl.stub(:foo)
|
170
|
-
|
171
|
-
stubbed_double.with(:arg) { :with_block }
|
172
|
-
expect(dbl.foo(:arg)).to eq(:with_block)
|
173
|
-
|
174
|
-
stubbed_double.at_least(:once) { :at_least_block }
|
175
|
-
expect(dbl.foo(:arg)).to eq(:at_least_block)
|
176
|
-
end
|
177
|
-
|
178
|
-
it 'raises an error if `and_call_original` is followed by any other instructions' do
|
179
|
-
dbl = [1, 2, 3]
|
180
|
-
stubbed = dbl.stub(:size)
|
181
|
-
stubbed.and_call_original
|
182
|
-
|
183
|
-
msg_fragment = /cannot be modified further/
|
184
|
-
|
185
|
-
expect { stubbed.and_yield }.to raise_error(msg_fragment)
|
186
|
-
expect { stubbed.and_return(1) }.to raise_error(msg_fragment)
|
187
|
-
expect { stubbed.and_raise("a") }.to raise_error(msg_fragment)
|
188
|
-
expect { stubbed.and_throw(:bar) }.to raise_error(msg_fragment)
|
189
|
-
|
190
|
-
expect { stubbed.once { } }.to raise_error(msg_fragment)
|
191
|
-
|
192
|
-
expect(dbl.size).to eq(3)
|
193
|
-
end
|
194
|
-
end
|
195
|
-
end
|
196
|
-
end
|
197
|
-
|