rspec-mocks 2.99.4 → 3.0.0.beta1

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.
Files changed (133) hide show
  1. checksums.yaml +14 -6
  2. checksums.yaml.gz.sig +2 -0
  3. data.tar.gz.sig +1 -0
  4. data/Changelog.md +89 -105
  5. data/License.txt +1 -0
  6. data/README.md +77 -57
  7. data/features/argument_matchers/explicit.feature +5 -5
  8. data/features/argument_matchers/general_matchers.feature +10 -10
  9. data/features/argument_matchers/type_matchers.feature +3 -3
  10. data/features/message_expectations/allow_any_instance_of.feature +1 -1
  11. data/features/message_expectations/any_instance.feature +27 -5
  12. data/features/message_expectations/call_original.feature +2 -2
  13. data/features/message_expectations/expect_message_using_expect.feature +2 -2
  14. data/features/message_expectations/expect_message_using_should_receive.feature +2 -2
  15. data/features/message_expectations/receive_counts.feature +7 -7
  16. data/features/message_expectations/warn_when_expectation_is_set_on_nil.feature +3 -3
  17. data/features/method_stubs/README.md +3 -0
  18. data/features/method_stubs/any_instance.feature +11 -11
  19. data/features/method_stubs/as_null_object.feature +4 -4
  20. data/features/method_stubs/simple_return_value_with_stub.feature +7 -7
  21. data/features/method_stubs/stub_chain.feature +3 -3
  22. data/features/method_stubs/stub_implementation.feature +2 -2
  23. data/features/method_stubs/to_ary.feature +2 -2
  24. data/features/mutating_constants/hiding_defined_constant.feature +2 -2
  25. data/features/mutating_constants/stub_defined_constant.feature +5 -5
  26. data/features/mutating_constants/stub_undefined_constant.feature +6 -6
  27. data/features/outside_rspec/configuration.feature +0 -2
  28. data/features/outside_rspec/standalone.feature +1 -1
  29. data/features/spies/spy_partial_mock_method.feature +2 -2
  30. data/features/spies/spy_pure_mock_method.feature +5 -5
  31. data/features/spies/spy_unstubbed_method.feature +1 -1
  32. data/features/support/env.rb +10 -1
  33. data/features/test_frameworks/test_unit.feature +1 -1
  34. data/features/verifying_doubles/class_doubles.feature +88 -0
  35. data/features/verifying_doubles/dynamic_classes.feature +72 -0
  36. data/features/verifying_doubles/introduction.feature +85 -0
  37. data/features/verifying_doubles/object_doubles.feature +65 -0
  38. data/features/verifying_doubles/partial_doubles.feature +34 -0
  39. data/lib/rspec/mocks.rb +8 -34
  40. data/lib/rspec/mocks/any_instance/chain.rb +4 -34
  41. data/lib/rspec/mocks/any_instance/expectation_chain.rb +14 -4
  42. data/lib/rspec/mocks/any_instance/message_chains.rb +27 -12
  43. data/lib/rspec/mocks/any_instance/recorder.rb +23 -31
  44. data/lib/rspec/mocks/any_instance/stub_chain.rb +9 -4
  45. data/lib/rspec/mocks/argument_list_matcher.rb +8 -1
  46. data/lib/rspec/mocks/argument_matchers.rb +26 -12
  47. data/lib/rspec/mocks/arity_calculator.rb +66 -0
  48. data/lib/rspec/mocks/configuration.rb +42 -14
  49. data/lib/rspec/mocks/error_generator.rb +34 -10
  50. data/lib/rspec/mocks/example_methods.rb +64 -19
  51. data/lib/rspec/mocks/extensions/marshal.rb +0 -15
  52. data/lib/rspec/mocks/framework.rb +4 -4
  53. data/lib/rspec/mocks/instance_method_stasher.rb +80 -62
  54. data/lib/rspec/mocks/matchers/have_received.rb +18 -14
  55. data/lib/rspec/mocks/matchers/receive.rb +29 -7
  56. data/lib/rspec/mocks/matchers/receive_messages.rb +72 -0
  57. data/lib/rspec/mocks/message_expectation.rb +95 -148
  58. data/lib/rspec/mocks/method_double.rb +77 -139
  59. data/lib/rspec/mocks/method_reference.rb +95 -0
  60. data/lib/rspec/mocks/mock.rb +1 -1
  61. data/lib/rspec/mocks/mutate_const.rb +12 -9
  62. data/lib/rspec/mocks/object_reference.rb +90 -0
  63. data/lib/rspec/mocks/order_group.rb +49 -7
  64. data/lib/rspec/mocks/proxy.rb +72 -33
  65. data/lib/rspec/mocks/proxy_for_nil.rb +2 -2
  66. data/lib/rspec/mocks/space.rb +13 -18
  67. data/lib/rspec/mocks/stub_chain.rb +2 -2
  68. data/lib/rspec/mocks/syntax.rb +61 -36
  69. data/lib/rspec/mocks/targets.rb +40 -19
  70. data/lib/rspec/mocks/test_double.rb +12 -56
  71. data/lib/rspec/mocks/verifying_double.rb +77 -0
  72. data/lib/rspec/mocks/verifying_message_expecation.rb +60 -0
  73. data/lib/rspec/mocks/verifying_proxy.rb +151 -0
  74. data/lib/rspec/mocks/version.rb +1 -1
  75. data/spec/rspec/mocks/and_call_original_spec.rb +34 -30
  76. data/spec/rspec/mocks/and_yield_spec.rb +2 -2
  77. data/spec/rspec/mocks/any_instance/message_chains_spec.rb +1 -1
  78. data/spec/rspec/mocks/any_instance_spec.rb +53 -260
  79. data/spec/rspec/mocks/argument_expectation_spec.rb +4 -4
  80. data/spec/rspec/mocks/arity_calculator_spec.rb +95 -0
  81. data/spec/rspec/mocks/array_including_matcher_spec.rb +41 -0
  82. data/spec/rspec/mocks/at_least_spec.rb +4 -32
  83. data/spec/rspec/mocks/block_return_value_spec.rb +4 -135
  84. data/spec/rspec/mocks/combining_implementation_instructions_spec.rb +10 -11
  85. data/spec/rspec/mocks/configuration_spec.rb +79 -0
  86. data/spec/rspec/mocks/double_spec.rb +10 -78
  87. data/spec/rspec/mocks/extensions/marshal_spec.rb +0 -8
  88. data/spec/rspec/mocks/failing_argument_matchers_spec.rb +49 -4
  89. data/spec/rspec/mocks/instance_method_stasher_spec.rb +20 -3
  90. data/spec/rspec/mocks/matchers/have_received_spec.rb +74 -0
  91. data/spec/rspec/mocks/matchers/receive_messages_spec.rb +140 -0
  92. data/spec/rspec/mocks/matchers/receive_spec.rb +82 -42
  93. data/spec/rspec/mocks/methods_spec.rb +1 -1
  94. data/spec/rspec/mocks/{bug_report_830_spec.rb → mock_expectation_error_spec.rb} +4 -3
  95. data/spec/rspec/mocks/mock_ordering_spec.rb +11 -0
  96. data/spec/rspec/mocks/mock_space_spec.rb +10 -1
  97. data/spec/rspec/mocks/mock_spec.rb +26 -82
  98. data/spec/rspec/mocks/multiple_return_value_spec.rb +1 -1
  99. data/spec/rspec/mocks/mutate_const_spec.rb +18 -5
  100. data/spec/rspec/mocks/null_object_mock_spec.rb +6 -4
  101. data/spec/rspec/mocks/options_hash_spec.rb +3 -3
  102. data/spec/rspec/mocks/order_group_spec.rb +27 -0
  103. data/spec/rspec/mocks/partial_mock_spec.rb +101 -1
  104. data/spec/rspec/mocks/passing_argument_matchers_spec.rb +3 -20
  105. data/spec/rspec/mocks/record_messages_spec.rb +4 -4
  106. data/spec/rspec/mocks/serialization_spec.rb +4 -6
  107. data/spec/rspec/mocks/space_spec.rb +3 -3
  108. data/spec/rspec/mocks/stub_chain_spec.rb +0 -12
  109. data/spec/rspec/mocks/stub_spec.rb +23 -44
  110. data/spec/rspec/mocks/test_double_spec.rb +3 -22
  111. data/spec/rspec/mocks/verifying_double_spec.rb +327 -0
  112. data/spec/rspec/mocks/verifying_message_expecation_spec.rb +68 -0
  113. data/spec/rspec/mocks_spec.rb +16 -39
  114. data/spec/spec_helper.rb +29 -18
  115. metadata +131 -86
  116. metadata.gz.sig +1 -0
  117. data/features/message_expectations/expect_any_instance_of.feature +0 -27
  118. data/lib/rspec/mocks/caller_filter.rb +0 -60
  119. data/lib/rspec/mocks/deprecation.rb +0 -26
  120. data/lib/rspec/mocks/extensions/instance_exec.rb +0 -34
  121. data/lib/rspec/mocks/extensions/proc.rb +0 -63
  122. data/lib/spec/mocks.rb +0 -4
  123. data/spec/rspec/mocks/and_return_spec.rb +0 -17
  124. data/spec/rspec/mocks/any_number_of_times_spec.rb +0 -36
  125. data/spec/rspec/mocks/before_all_spec.rb +0 -74
  126. data/spec/rspec/mocks/bug_report_10260_spec.rb +0 -8
  127. data/spec/rspec/mocks/bug_report_10263_spec.rb +0 -27
  128. data/spec/rspec/mocks/bug_report_11545_spec.rb +0 -32
  129. data/spec/rspec/mocks/bug_report_496_spec.rb +0 -17
  130. data/spec/rspec/mocks/bug_report_600_spec.rb +0 -22
  131. data/spec/rspec/mocks/bug_report_7611_spec.rb +0 -16
  132. data/spec/rspec/mocks/bug_report_8165_spec.rb +0 -31
  133. data/spec/rspec/mocks/bug_report_957_spec.rb +0 -22
@@ -1,9 +1,9 @@
1
1
  module RSpec
2
2
  module Mocks
3
3
  # @private
4
- class MethodDouble < Hash
4
+ class MethodDouble
5
5
  # @private
6
- attr_reader :method_name, :object
6
+ attr_reader :method_name, :object, :expectations, :stubs
7
7
 
8
8
  # @private
9
9
  def initialize(object, method_name, proxy)
@@ -11,21 +11,27 @@ module RSpec
11
11
  @object = object
12
12
  @proxy = proxy
13
13
 
14
- @method_stasher = InstanceMethodStasher.new(object_singleton_class, @method_name)
14
+ @original_visibility = nil
15
+ @method_stasher = InstanceMethodStasher.new(object, method_name)
15
16
  @method_is_proxied = false
16
- store(:expectations, [])
17
- store(:stubs, [])
17
+ @expectations = []
18
+ @stubs = []
18
19
  end
19
20
 
20
- # @private
21
- def expectations
22
- self[:expectations]
21
+ def original_method
22
+ # If original method is not present, uses the `method_missing`
23
+ # handler of the object. This accounts for cases where the user has not
24
+ # correctly defined `respond_to?`, and also 1.8 which does not provide
25
+ # method handles for missing methods even if `respond_to?` is correct.
26
+ @original_method ||=
27
+ @method_stasher.original_method ||
28
+ @proxy.method_handle_for(method_name) ||
29
+ Proc.new do |*args, &block|
30
+ @object.__send__(:method_missing, @method_name, *args, &block)
31
+ end
23
32
  end
24
33
 
25
- # @private
26
- def stubs
27
- self[:stubs]
28
- end
34
+ alias_method :save_original_method!, :original_method
29
35
 
30
36
  # @private
31
37
  def visibility
@@ -40,119 +46,6 @@ module RSpec
40
46
  end
41
47
  end
42
48
 
43
- class ProcWithBlock < Struct.new(:object, :method_name)
44
-
45
- def call(*args, &block)
46
- self.object.__send__(:method_missing, self.method_name, *args, &block)
47
- end
48
-
49
- end
50
-
51
- # @private
52
- def original_method
53
- if @method_stasher.method_is_stashed?
54
- # Example: a singleton method defined on @object
55
- ::RSpec::Mocks.method_handle_for(@object, @method_stasher.stashed_method_name)
56
- elsif meth = original_unrecorded_any_instance_method
57
- # Example: a method that has been mocked through
58
- # klass.any_instance.should_receive(:msg).and_call_original
59
- # any_instance.should_receive(:msg) causes the method to be
60
- # replaced with a proxy method, and then `and_call_original`
61
- # is recorded and played back on the object instance. We need
62
- # special handling here to get a handle on the original method
63
- # object rather than the proxy method.
64
- meth
65
- else
66
- # Example: an instance method defined on one of @object's ancestors.
67
- original_method_from_ancestry
68
- end
69
- rescue NameError
70
- # We have no way of knowing if the object's method_missing
71
- # will handle this message or not...but we can at least try.
72
- # If it's not handled, a `NoMethodError` will be raised, just
73
- # like normally.
74
- ProcWithBlock.new(@object,@method_name)
75
- end
76
-
77
- def original_unrecorded_any_instance_method
78
- return nil unless any_instance_class_recorder_observing_method?(@object.class)
79
- alias_name = ::RSpec::Mocks.any_instance_recorder_for(@object.class).build_alias_method_name(@method_name)
80
- @object.method(alias_name)
81
- end
82
-
83
- def any_instance_class_recorder_observing_method?(klass)
84
- return true if ::RSpec::Mocks.any_instance_recorder_for(klass).already_observing?(@method_name)
85
- superklass = klass.superclass
86
- return false if superklass.nil?
87
- any_instance_class_recorder_observing_method?(superklass)
88
- end
89
-
90
- our_singleton_class = class << self; self; end
91
- if our_singleton_class.ancestors.include? our_singleton_class
92
- # In Ruby 2.1, ancestors include the correct ancestors, including the singleton classes
93
- def original_method_from_ancestry
94
- # Lookup in the ancestry, skipping over the singleton class itself
95
- original_method_from_ancestor(object_singleton_class.ancestors.drop(1))
96
- end
97
- else
98
- # @private
99
- def original_method_from_ancestry
100
- original_method_from_ancestor(object_singleton_class.ancestors)
101
- rescue NameError
102
- raise unless @object.respond_to?(:superclass)
103
-
104
- # Example: a singleton method defined on @object's superclass.
105
- #
106
- # Note: we have to give precedence to instance methods
107
- # defined on @object's class, because in a case like:
108
- #
109
- # `klass.should_receive(:new).and_call_original`
110
- #
111
- # ...we want `Class#new` bound to `klass` (which will return
112
- # an instance of `klass`), not `klass.superclass.new` (which
113
- # would return an instance of `klass.superclass`).
114
- original_method_from_superclass
115
- end
116
- end
117
-
118
- def original_method_from_ancestor(ancestors)
119
- klass, *rest = ancestors
120
- klass.instance_method(@method_name).bind(@object)
121
- rescue NameError
122
- raise if rest.empty?
123
- original_method_from_ancestor(rest)
124
- end
125
-
126
- if RUBY_VERSION.to_f > 1.8
127
- # @private
128
- def original_method_from_superclass
129
- @object.superclass.
130
- singleton_class.
131
- instance_method(@method_name).
132
- bind(@object)
133
- end
134
- else
135
- # Our implementation for 1.9 (above) causes an error on 1.8:
136
- # TypeError: singleton method bound for a different object
137
- #
138
- # This doesn't work quite right in all circumstances but it's the
139
- # best we can do.
140
- # @private
141
- def original_method_from_superclass
142
- ::Kernel.warn <<-WARNING.gsub(/^ +\|/, '')
143
- |
144
- |WARNING: On ruby 1.8, rspec-mocks is unable to bind the original
145
- |`#{@method_name}` method to your partial mock object (#{@object})
146
- |for `and_call_original`. The superclass's `#{@method_name}` is being
147
- |used instead; however, it may not work correctly when executed due
148
- |to the fact that `self` will be #{@object.superclass}, not #{@object}.
149
- |
150
- |Called from: #{CallerFilter.first_non_rspec_line}
151
- WARNING
152
-
153
- @object.superclass.method(@method_name)
154
- end
155
- end
156
49
  # @private
157
50
  def object_singleton_class
158
51
  class << @object; self; end
@@ -160,7 +53,7 @@ module RSpec
160
53
 
161
54
  # @private
162
55
  def configure_method
163
- @original_visibility = visibility_for_method
56
+ @original_visibility = [visibility, method_name]
164
57
  @method_stasher.stash unless @method_is_proxied
165
58
  define_proxy_method
166
59
  end
@@ -169,18 +62,24 @@ module RSpec
169
62
  def define_proxy_method
170
63
  return if @method_is_proxied
171
64
 
172
- object_singleton_class.class_eval <<-EOF, __FILE__, __LINE__ + 1
173
- def #{@method_name}(*args, &block)
174
- ::RSpec::Mocks.proxy_for(self).message_received :#{@method_name}, *args, &block
65
+ save_original_method!
66
+
67
+ object_singleton_class.class_exec(self, method_name, visibility) do |method_double, method_name, visibility|
68
+ define_method(method_name) do |*args, &block|
69
+ method_double.proxy_method_invoked(self, *args, &block)
175
70
  end
176
- #{visibility_for_method}
177
- EOF
71
+ self.__send__ visibility, method_name
72
+ end
73
+
178
74
  @method_is_proxied = true
179
75
  end
180
76
 
77
+ # The implementation of the proxied method. Subclasses may override this
78
+ # method to perform additional operations.
79
+ #
181
80
  # @private
182
- def visibility_for_method
183
- "#{visibility} :#{method_name}"
81
+ def proxy_method_invoked(obj, *args, &block)
82
+ @proxy.message_received method_name, *args, &block
184
83
  end
185
84
 
186
85
  # @private
@@ -188,7 +87,9 @@ module RSpec
188
87
  return unless @method_is_proxied
189
88
 
190
89
  object_singleton_class.__send__(:remove_method, @method_name)
191
- @method_stasher.restore
90
+ if @method_stasher.method_is_stashed?
91
+ @method_stasher.restore
92
+ end
192
93
  restore_original_visibility
193
94
 
194
95
  @method_is_proxied = false
@@ -196,8 +97,11 @@ module RSpec
196
97
 
197
98
  # @private
198
99
  def restore_original_visibility
199
- return unless object_singleton_class.method_defined?(@method_name) || object_singleton_class.private_method_defined?(@method_name)
200
- object_singleton_class.class_eval(@original_visibility, __FILE__, __LINE__ + 1)
100
+ return unless @original_visibility &&
101
+ (object_singleton_class.method_defined?(@method_name) ||
102
+ object_singleton_class.private_method_defined?(@method_name))
103
+
104
+ object_singleton_class.__send__(*@original_visibility)
201
105
  end
202
106
 
203
107
  # @private
@@ -217,10 +121,18 @@ module RSpec
217
121
  stubs.clear
218
122
  end
219
123
 
124
+ # The type of message expectation to create has been extracted to its own
125
+ # method so that subclasses can override it.
126
+ #
127
+ # @private
128
+ def message_expectation_class
129
+ MessageExpectation
130
+ end
131
+
220
132
  # @private
221
133
  def add_expectation(error_generator, expectation_ordering, expected_from, opts, &implementation)
222
134
  configure_method
223
- expectation = MessageExpectation.new(error_generator, expectation_ordering,
135
+ expectation = message_expectation_class.new(error_generator, expectation_ordering,
224
136
  expected_from, self, 1, opts, &implementation)
225
137
  expectations << expectation
226
138
  expectation
@@ -229,18 +141,44 @@ module RSpec
229
141
  # @private
230
142
  def build_expectation(error_generator, expectation_ordering)
231
143
  expected_from = IGNORED_BACKTRACE_LINE
232
- MessageExpectation.new(error_generator, expectation_ordering, expected_from, self)
144
+ message_expectation_class.new(error_generator, expectation_ordering, expected_from, self)
233
145
  end
234
146
 
235
147
  # @private
236
148
  def add_stub(error_generator, expectation_ordering, expected_from, opts={}, &implementation)
237
149
  configure_method
238
- stub = MessageExpectation.new(error_generator, expectation_ordering, expected_from,
150
+ stub = message_expectation_class.new(error_generator, expectation_ordering, expected_from,
239
151
  self, :any, opts, &implementation)
240
152
  stubs.unshift stub
241
153
  stub
242
154
  end
243
155
 
156
+ # A simple stub can only return a concrete value for a message, and
157
+ # cannot match on arguments. It is used as an optimization over
158
+ # `add_stub` / `add_expectation` where it is known in advance that this
159
+ # is all that will be required of a stub, such as when passing attributes
160
+ # to the `double` example method. They do not stash or restore existing method
161
+ # definitions.
162
+ #
163
+ # @private
164
+ def add_simple_stub(method_name, response)
165
+ setup_simple_method_double method_name, response, stubs
166
+ end
167
+
168
+ # @private
169
+ def add_simple_expectation(method_name, response, error_generator, backtrace_line)
170
+ setup_simple_method_double method_name, response, expectations, error_generator, backtrace_line
171
+ end
172
+
173
+ # @private
174
+ def setup_simple_method_double(method_name, response, collection, error_generator = nil, backtrace_line = nil)
175
+ define_proxy_method
176
+
177
+ me = SimpleMessageExpectation.new(method_name, response, error_generator, backtrace_line)
178
+ collection.unshift me
179
+ me
180
+ end
181
+
244
182
  # @private
245
183
  def add_default_stub(*args, &implementation)
246
184
  return if stubs.any?
@@ -0,0 +1,95 @@
1
+ module RSpec
2
+ module Mocks
3
+ # Represents a method on a module that may or may not be defined.
4
+ #
5
+ # @private
6
+ class MethodReference
7
+ def initialize(module_reference, method_name)
8
+ @module_reference = module_reference
9
+ @method_name = method_name
10
+ end
11
+
12
+ # A method is implemented if sending the message does not result in
13
+ # a `NoMethodError`. It might be dynamically implemented by
14
+ # `method_missing`.
15
+ def implemented?
16
+ @module_reference.when_loaded do |m|
17
+ method_implemented?(m)
18
+ end
19
+ end
20
+
21
+ # A method is defined if we are able to get a `Method` object for it.
22
+ # In that case, we can assert against metadata like the arity.
23
+ def defined?
24
+ @module_reference.when_loaded do |m|
25
+ method_defined?(m)
26
+ end
27
+ end
28
+
29
+ def when_defined
30
+ if original = original_method
31
+ yield original
32
+ end
33
+ end
34
+
35
+ # Yields to the block if the method is not implemented.
36
+ def when_unimplemented
37
+ yield unless implemented?
38
+ end
39
+
40
+ private
41
+ def original_method
42
+ @module_reference.when_loaded do |m|
43
+ self.defined? && find_method(m)
44
+ end
45
+ end
46
+ end
47
+
48
+ # @private
49
+ class InstanceMethodReference < MethodReference
50
+ private
51
+ def method_implemented?(m)
52
+ m.method_defined?(@method_name)
53
+ end
54
+
55
+ # Ideally, we'd use `respond_to?` for `method_implemented?` but we need a
56
+ # reference to an instance to do that and we don't have one. Note that
57
+ # we may get false negatives: if the method is implemented via
58
+ # `method_missing`, we'll return `false` even though it meets our
59
+ # definition of "implemented". However, it's the best we can do.
60
+ alias method_defined? method_implemented?
61
+
62
+ # works around the fact that repeated calls for method parameters will
63
+ # falsely return empty arrays on JRuby in certain circumstances, this
64
+ # is necessary here because we can't dup/clone UnboundMethods.
65
+ #
66
+ # This is necessary due to a bug in JRuby prior to 1.7.5 fixed in:
67
+ # https://github.com/jruby/jruby/commit/99a0613fe29935150d76a9a1ee4cf2b4f63f4a27
68
+ if RUBY_PLATFORM == 'java' && JRUBY_VERSION.split('.')[-1].to_i < 5
69
+ def find_method(m)
70
+ m.dup.instance_method(@method_name)
71
+ end
72
+ else
73
+ def find_method(m)
74
+ m.instance_method(@method_name)
75
+ end
76
+ end
77
+ end
78
+
79
+ # @private
80
+ class ObjectMethodReference < MethodReference
81
+ private
82
+ def method_implemented?(m)
83
+ m.respond_to?(@method_name)
84
+ end
85
+
86
+ def method_defined?(m)
87
+ (class << m; self; end).method_defined?(@method_name)
88
+ end
89
+
90
+ def find_method(m)
91
+ m.method(@method_name)
92
+ end
93
+ end
94
+ end
95
+ end
@@ -1,6 +1,6 @@
1
1
  module RSpec
2
2
  module Mocks
3
- class Double
3
+ class Mock
4
4
  include TestDouble
5
5
  end
6
6
  end
@@ -64,7 +64,7 @@ module RSpec
64
64
 
65
65
  def recursive_const_defined?(const_name)
66
66
  normalize_const_name(const_name).split('::').inject([Object, '']) do |(mod, full_name), name|
67
- yield(full_name, name) if block_given? && !mod.is_a?(Module)
67
+ yield(full_name, name) if block_given? && !(Module === mod)
68
68
  return false unless const_defined_on?(mod, name)
69
69
  [get_const_defined_on(mod, name), [mod, name].join('::')]
70
70
  end
@@ -167,16 +167,16 @@ module RSpec
167
167
  # so you can stub constants in other contexts (e.g. helper
168
168
  # classes).
169
169
  def self.stub(constant_name, value, options = {})
170
- space = RSpec::Mocks.space
171
- space.print_out_of_example_deprecation if space.outside_example
172
-
173
170
  mutator = if recursive_const_defined?(constant_name, &raise_on_invalid_const)
174
171
  DefinedConstantReplacer
175
172
  else
176
173
  UndefinedConstantSetter
177
174
  end
178
175
 
179
- mutate(mutator.new(constant_name, value, options[:transfer_nested_constants]))
176
+ mutate(mutator.new(constant_name, value, options.fetch(
177
+ :transfer_nested_constants,
178
+ RSpec::Mocks.configuration.transfer_nested_constants?
179
+ )))
180
180
  value
181
181
  end
182
182
 
@@ -190,9 +190,6 @@ module RSpec
190
190
  # so you can hide constants in other contexts (e.g. helper
191
191
  # classes).
192
192
  def self.hide(constant_name)
193
- space = RSpec::Mocks.space
194
- space.print_out_of_example_deprecation if space.outside_example
195
-
196
193
  return unless recursive_const_defined?(constant_name)
197
194
 
198
195
  mutate(ConstantHider.new(constant_name, nil, { }))
@@ -294,7 +291,7 @@ module RSpec
294
291
  end
295
292
  end
296
293
 
297
- if @transfer_nested_constants.is_a?(Array)
294
+ if Array === @transfer_nested_constants
298
295
  @transfer_nested_constants = @transfer_nested_constants.map(&:to_s) if RUBY_VERSION == '1.8.7'
299
296
  undefined_constants = @transfer_nested_constants - constants_defined_on(@original_value)
300
297
 
@@ -399,5 +396,11 @@ module RSpec
399
396
  end
400
397
  end
401
398
  end
399
+
400
+ # Keeps backwards compatibility since we had released an rspec-mocks that
401
+ # only supported stubbing. Later, we released the hide_const feature and
402
+ # decided that the term "mutator" was a better term to wrap up the concept
403
+ # of both stubbing and hiding.
404
+ ConstantStubber = ConstantMutator
402
405
  end
403
406
  end