Name | Total Lines | Lines of Code | Total Coverage | Code Coverage |
---|---|---|---|---|
rcov/ruby/1.8/gems/rspec-mocks-2.5.0/lib/rspec/mocks.rb | 196 | 23 | 100.00%
|
100.00%
|
Code reported as executed by Ruby looks like this...and this: this line is also marked as covered.Lines considered as run by rcov, but not reported by Ruby, look like this,and this: these lines were inferred by rcov (using simple heuristics).Finally, here's a line marked as not executed.
1 require 'rspec/mocks/framework' |
2 require 'rspec/mocks/version' |
3 require 'rspec/mocks/spec_methods' |
4 |
5 module RSpec |
6 # == Test Doubles |
7 # |
8 # A Test Double is an object that stands in for a real object in a test. |
9 # RSpec creates test doubles that support method stubs and message |
10 # expectations. |
11 # |
12 # book = double("book") |
13 # |
14 # == Method Stubs |
15 # |
16 # A method stub is an implementation that returns a pre-determined value. |
17 # |
18 # book = double("book") |
19 # double.stub(:title) { "The RSpec Book" } |
20 # double.title => "The RSpec Book" |
21 # |
22 # When we declare a stub, we say we are "stubbing" a method. |
23 # |
24 # == Message Expectations |
25 # |
26 # A message expectation is an expectation that the test double will receive a |
27 # message some time before the example ends. If the message is received, the |
28 # expectation is satisfied. If not, the example fails. |
29 # |
30 # validator = double("validator") |
31 # validator.should_receive(:validate).with("02134") |
32 # zipcode = Zipcode.new("02134", validator) |
33 # zipcode.valid? |
34 # |
35 # When we declare a message expectation, we say we are "mocking" a method. |
36 # |
37 # == Mock Objects and Test Stubs |
38 # |
39 # The names Mock Object and Test Stub suggest specialized Test Doubles. i.e. |
40 # Test Stub evokes Test Double that only supports method stubs, and a Mock |
41 # Object evokes a Test Double that only supports message expectations, or |
42 # sometimes supports message expectations in addition to method stubs. |
43 # |
44 # There is a lot of overlapping nomenclature here, and there are many |
45 # variations of these patterns (fakes, spies, etc). Keep in mind that most of |
46 # the time we're talking about method-level concepts that are variations of |
47 # method stubs and message expectations, and we're applying to them to _one_ |
48 # generic kind of object: a Test Double. |
49 # |
50 # == Test-Specific Extension |
51 # |
52 # a.k.a. Partial Stub/Mock, a Test-Specific Extension is an extension of a |
53 # real object in a system that is instrumented with test-double like |
54 # behaviour in the context of a test. This technique is very common in Ruby |
55 # because we often see class objects acting as global namespaces for methods. |
56 # For example, in Rails: |
57 # |
58 # person = double("person") |
59 # Person.stub(:find) { person } |
60 # |
61 # In this case we're instrumenting Person to return the person object we've |
62 # defined whenever it receives the +find+ message. We can do this with any |
63 # object in a system because RSpec adds the +stub+ and +should_receive+ |
64 # methods to every object. When we use either, RSpec replaces the method |
65 # we're stubbing or mocking with it's own test-double-like method. At the |
66 # end of the example, RSpec verifies any message expectations, and then |
67 # restores the original methods. |
68 # |
69 # == Expecting Arguments |
70 # |
71 # double.should_receive(:msg).with(*args) |
72 # double.should_not_receive(:msg).with(*args) |
73 # |
74 # == Argument Matchers |
75 # |
76 # Arguments that are passed to #with are compared with actual arguments received |
77 # using == by default. In cases in which you want to specify things about the arguments |
78 # rather than the arguments themselves, you can use any of RSpec's Expression Matchers. |
79 # They don't all make syntactic sense (they were primarily designed for use with |
80 # RSpec::Expectations), but you are free to create your own custom RSpec::Matchers. |
81 # |
82 # RSpec::Mocks does provide one additional Matcher method named #ducktype. |
83 # |
84 # In addition, RSpec::Mocks adds some keyword Symbols that you can use to |
85 # specify certain kinds of arguments: |
86 # |
87 # double.should_receive(:msg).with(no_args()) |
88 # double.should_receive(:msg).with(any_args()) |
89 # double.should_receive(:msg).with(1, kind_of(Numeric), "b") #2nd argument can any kind of Numeric |
90 # double.should_receive(:msg).with(1, boolean(), "b") #2nd argument can true or false |
91 # double.should_receive(:msg).with(1, /abc/, "b") #2nd argument can be any String matching the submitted Regexp |
92 # double.should_receive(:msg).with(1, anything(), "b") #2nd argument can be anything at all |
93 # double.should_receive(:msg).with(1, ducktype(:abs, :div), "b") |
94 # #2nd argument can be object that responds to #abs and #div |
95 # |
96 # == Receive Counts |
97 # |
98 # double.should_receive(:msg).once |
99 # double.should_receive(:msg).twice |
100 # double.should_receive(:msg).exactly(n).times |
101 # double.should_receive(:msg).at_least(:once) |
102 # double.should_receive(:msg).at_least(:twice) |
103 # double.should_receive(:msg).at_least(n).times |
104 # double.should_receive(:msg).at_most(:once) |
105 # double.should_receive(:msg).at_most(:twice) |
106 # double.should_receive(:msg).at_most(n).times |
107 # double.should_receive(:msg).any_number_of_times |
108 # |
109 # == Ordering |
110 # |
111 # double.should_receive(:msg).ordered |
112 # double.should_receive(:other_msg).ordered |
113 # #This will fail if the messages are received out of order |
114 # |
115 # == Setting Reponses |
116 # |
117 # Whether you are setting a message expectation or a method stub, you can |
118 # tell the object precisely how to respond. The most generic way is to pass |
119 # a block to +stub+ or +should_receive+: |
120 # |
121 # double.should_receive(:msg) { value } |
122 # |
123 # When the double receives the +msg+ message, it evaluates the block and returns |
124 # the result. |
125 # |
126 # double.should_receive(:msg).and_return(value) |
127 # double.should_receive(:msg).exactly(3).times.and_return(value1, value2, value3) |
128 # # returns value1 the first time, value2 the second, etc |
129 # double.should_receive(:msg).and_raise(error) |
130 # #error can be an instantiated object or a class |
131 # #if it is a class, it must be instantiable with no args |
132 # double.should_receive(:msg).and_throw(:msg) |
133 # double.should_receive(:msg).and_yield(values,to,yield) |
134 # double.should_receive(:msg).and_yield(values,to,yield).and_yield(some,other,values,this,time) |
135 # # for methods that yield to a block multiple times |
136 # |
137 # Any of these responses can be applied to a stub as well |
138 # |
139 # double.stub(:msg).and_return(value) |
140 # double.stub(:msg).and_return(value1, value2, value3) |
141 # double.stub(:msg).and_raise(error) |
142 # double.stub(:msg).and_throw(:msg) |
143 # double.stub(:msg).and_yield(values,to,yield) |
144 # double.stub(:msg).and_yield(values,to,yield).and_yield(some,other,values,this,time) |
145 # |
146 # == Arbitrary Handling |
147 # |
148 # Once in a while you'll find that the available expectations don't solve the |
149 # particular problem you are trying to solve. Imagine that you expect the message |
150 # to come with an Array argument that has a specific length, but you don't care |
151 # what is in it. You could do this: |
152 # |
153 # double.should_receive(:msg) do |arg| |
154 # arg.should be_an_istance_of(Array) |
155 # arg.length.should == 7 |
156 # end |
157 # |
158 # == Combining Expectation Details |
159 # |
160 # Combining the message name with specific arguments, receive counts and responses |
161 # you can get quite a bit of detail in your expectations: |
162 # |
163 # double.should_receive(:<<).with("illegal value").once.and_raise(ArgumentError) |
164 # |
165 # == Further Reading |
166 # |
167 # There are many different viewpoints about the meaning of mocks and stubs. If you are interested |
168 # in learning more, here is some recommended reading: |
169 # |
170 # * Mock Objects: http://www.mockobjects.com/ |
171 # * Endo-Testing: http://www.mockobjects.com/files/endotesting.pdf |
172 # * Mock Roles, Not Objects: http://www.mockobjects.com/files/mockrolesnotobjects.pdf |
173 # * Test Double Patterns: http://xunitpatterns.com/Test%20Double%20Patterns.html |
174 # * Mocks aren't stubs: http://www.martinfowler.com/articles/mocksArentStubs.html |
175 module Mocks |
176 class << self |
177 attr_accessor :space |
178 |
179 def setup(includer) |
180 Object.class_eval { include RSpec::Mocks::Methods } unless Object < RSpec::Mocks::Methods |
181 (class << includer; self; end).class_eval do |
182 include RSpec::Mocks::ExampleMethods |
183 end |
184 self.space ||= RSpec::Mocks::Space.new |
185 end |
186 |
187 def verify |
188 space.verify_all |
189 end |
190 |
191 def teardown |
192 space.reset_all |
193 end |
194 end |
195 end |
196 end |
Generated on Fri Apr 22 17:22:42 -0700 2011 with rcov 0.9.8