rr 0.2.5 → 0.3.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (40) hide show
  1. data/CHANGES +5 -0
  2. data/README +20 -9
  3. data/Rakefile +1 -1
  4. data/examples/example_suite.rb +1 -1
  5. data/examples/high_level_example.rb +4 -4
  6. data/examples/rr/double/double_dispatching_example.rb +41 -41
  7. data/examples/rr/double/double_verify_example.rb +1 -1
  8. data/examples/rr/expectations/times_called_expectation/times_called_expectation_helper.rb +2 -2
  9. data/examples/rr/extensions/instance_methods_creator_example.rb +48 -38
  10. data/examples/rr/extensions/instance_methods_space_example.rb +8 -8
  11. data/examples/rr/rspec/rspec_adapter_example.rb +9 -9
  12. data/examples/rr/rspec/rspec_usage_example.rb +16 -2
  13. data/examples/rr/scenario_creator_example.rb +400 -0
  14. data/examples/rr/scenario_example.rb +19 -4
  15. data/examples/rr/scenario_method_proxy_example.rb +71 -0
  16. data/examples/rr/space/space_create_example.rb +93 -106
  17. data/examples/rr/space/space_example.rb +2 -2
  18. data/examples/rr/space/space_register_example.rb +3 -3
  19. data/examples/rr/space/space_reset_example.rb +11 -11
  20. data/examples/rr/space/space_verify_example.rb +12 -12
  21. data/examples/rr/test_unit/test_unit_integration_test.rb +11 -2
  22. data/lib/rr.rb +10 -12
  23. data/lib/rr/errors/scenario_definition_error.rb +6 -0
  24. data/lib/rr/extensions/instance_methods.rb +84 -84
  25. data/lib/rr/scenario.rb +18 -3
  26. data/lib/rr/scenario_creator.rb +233 -0
  27. data/lib/rr/scenario_method_proxy.rb +19 -0
  28. data/lib/rr/space.rb +12 -32
  29. metadata +7 -13
  30. data/examples/rr/do_not_allow_creator_example.rb +0 -111
  31. data/examples/rr/mock_creator_example.rb +0 -87
  32. data/examples/rr/mock_probe_creator_example.rb +0 -120
  33. data/examples/rr/stub_creator_example.rb +0 -96
  34. data/examples/rr/stub_probe_creator_example.rb +0 -127
  35. data/lib/rr/creator.rb +0 -16
  36. data/lib/rr/do_not_allow_creator.rb +0 -33
  37. data/lib/rr/mock_creator.rb +0 -26
  38. data/lib/rr/mock_probe_creator.rb +0 -36
  39. data/lib/rr/stub_creator.rb +0 -30
  40. data/lib/rr/stub_probe_creator.rb +0 -42
@@ -17,12 +17,12 @@ describe Space, " class" do
17
17
  it "proxies to a singleton instance of Space" do
18
18
  create_double_args = nil
19
19
  (class << @space; self; end).class_eval do
20
- define_method :create_double do |*args|
20
+ define_method :double do |*args|
21
21
  create_double_args = args
22
22
  end
23
23
  end
24
24
 
25
- Space.create_double(:foo, :bar)
25
+ Space.double(:foo, :bar)
26
26
  create_double_args.should == [:foo, :bar]
27
27
  end
28
28
  end
@@ -10,7 +10,7 @@ describe Space, "#register_ordered_scenario" do
10
10
  Space.instance = @space
11
11
  @object = Object.new
12
12
  @method_name = :foobar
13
- @double = @space.create_double(@object, @method_name)
13
+ @double = @space.double(@object, @method_name)
14
14
  end
15
15
 
16
16
  after(:each) do
@@ -18,13 +18,13 @@ describe Space, "#register_ordered_scenario" do
18
18
  end
19
19
 
20
20
  it "adds the ordered scenario to the ordered_scenarios collection" do
21
- scenario1 = @space.create_scenario(@double)
21
+ scenario1 = @space.scenario(@double)
22
22
 
23
23
  @space.ordered_scenarios.should == []
24
24
  @space.register_ordered_scenario scenario1
25
25
  @space.ordered_scenarios.should == [scenario1]
26
26
 
27
- scenario2 = @space.create_scenario(@double)
27
+ scenario2 = @space.scenario(@double)
28
28
  @space.register_ordered_scenario scenario2
29
29
  @space.ordered_scenarios.should == [scenario1, scenario2]
30
30
  end
@@ -12,11 +12,11 @@ describe Space, "#reset" do
12
12
  end
13
13
 
14
14
  it "removes the ordered scenarios" do
15
- double1 = @space.create_double(@object1, :foobar1)
16
- double2 = @space.create_double(@object1, :foobar2)
15
+ double1 = @space.double(@object1, :foobar1)
16
+ double2 = @space.double(@object1, :foobar2)
17
17
 
18
- scenario1 = @space.create_scenario(double1)
19
- scenario2 = @space.create_scenario(double2)
18
+ scenario1 = @space.scenario(double1)
19
+ scenario2 = @space.scenario(double2)
20
20
 
21
21
  scenario1.ordered
22
22
  scenario2.ordered
@@ -28,14 +28,14 @@ describe Space, "#reset" do
28
28
  end
29
29
 
30
30
  it "resets all doubles" do
31
- double1 = @space.create_double(@object1, @method_name)
31
+ double1 = @space.double(@object1, @method_name)
32
32
  double1_reset_calls = 0
33
33
  (class << double1; self; end).class_eval do
34
34
  define_method(:reset) do ||
35
35
  double1_reset_calls += 1
36
36
  end
37
37
  end
38
- double2 = @space.create_double(@object2, @method_name)
38
+ double2 = @space.double(@object2, @method_name)
39
39
  double2_reset_calls = 0
40
40
  (class << double2; self; end).class_eval do
41
41
  define_method(:reset) do ||
@@ -59,7 +59,7 @@ describe Space, "#reset_double" do
59
59
  end
60
60
 
61
61
  it "resets the doubles" do
62
- double = @space.create_double(@object, @method_name)
62
+ double = @space.double(@object, @method_name)
63
63
  @space.doubles[@object][@method_name].should === double
64
64
  @object.methods.should include("__rr__#{@method_name}")
65
65
 
@@ -69,8 +69,8 @@ describe Space, "#reset_double" do
69
69
  end
70
70
 
71
71
  it "removes the object from the doubles map when it has no doubles" do
72
- double1 = @space.create_double(@object, :foobar1)
73
- double2 = @space.create_double(@object, :foobar2)
72
+ double1 = @space.double(@object, :foobar1)
73
+ double2 = @space.double(@object, :foobar2)
74
74
 
75
75
  @space.doubles.include?(@object).should == true
76
76
  @space.doubles[@object][:foobar1].should_not be_nil
@@ -97,14 +97,14 @@ describe Space, "#reset_doubles" do
97
97
  end
98
98
 
99
99
  it "resets the double and removes it from the doubles list" do
100
- double1 = @space.create_double(@object1, @method_name)
100
+ double1 = @space.double(@object1, @method_name)
101
101
  double1_reset_calls = 0
102
102
  (class << double1; self; end).class_eval do
103
103
  define_method(:reset) do ||
104
104
  double1_reset_calls += 1
105
105
  end
106
106
  end
107
- double2 = @space.create_double(@object2, @method_name)
107
+ double2 = @space.double(@object2, @method_name)
108
108
  double2_reset_calls = 0
109
109
  (class << double2; self; end).class_eval do
110
110
  define_method(:reset) do ||
@@ -12,7 +12,7 @@ describe Space, "#verify_doubles" do
12
12
  end
13
13
 
14
14
  it "verifies and deletes the doubles" do
15
- double1 = @space.create_double(@object1, @method_name)
15
+ double1 = @space.double(@object1, @method_name)
16
16
  double1_verify_calls = 0
17
17
  double1_reset_calls = 0
18
18
  (class << double1; self; end).class_eval do
@@ -23,7 +23,7 @@ describe Space, "#verify_doubles" do
23
23
  double1_reset_calls += 1
24
24
  end
25
25
  end
26
- double2 = @space.create_double(@object2, @method_name)
26
+ double2 = @space.double(@object2, @method_name)
27
27
  double2_verify_calls = 0
28
28
  double2_reset_calls = 0
29
29
  (class << double2; self; end).class_eval do
@@ -53,7 +53,7 @@ describe Space, "#verify_double" do
53
53
  end
54
54
 
55
55
  it "verifies and deletes the double" do
56
- double = @space.create_double(@object, @method_name)
56
+ double = @space.double(@object, @method_name)
57
57
  @space.doubles[@object][@method_name].should === double
58
58
  @object.methods.should include("__rr__#{@method_name}")
59
59
 
@@ -71,7 +71,7 @@ describe Space, "#verify_double" do
71
71
  end
72
72
 
73
73
  it "deletes the double when verifying the double raises an error" do
74
- double = @space.create_double(@object, @method_name)
74
+ double = @space.double(@object, @method_name)
75
75
  @space.doubles[@object][@method_name].should === double
76
76
  @object.methods.should include("__rr__#{@method_name}")
77
77
 
@@ -97,11 +97,11 @@ describe Space, "#verify_ordered_scenario", :shared => true do
97
97
  @space = Space.new
98
98
  @object = Object.new
99
99
  @method_name = :foobar
100
- @double = @space.create_double(@object, @method_name)
100
+ @double = @space.double(@object, @method_name)
101
101
  end
102
102
 
103
103
  it "raises an error when Scenario is NonTerminal" do
104
- scenario = @space.create_scenario(@double)
104
+ scenario = @space.scenario(@double)
105
105
  @space.register_ordered_scenario(scenario)
106
106
 
107
107
  scenario.any_number_of_times
@@ -120,7 +120,7 @@ describe Space, "#verify_ordered_scenario where the passed in scenario is at the
120
120
  it_should_behave_like "RR::Space#verify_ordered_scenario"
121
121
 
122
122
  it "keeps the scenario when times called is not verified" do
123
- scenario = @space.create_scenario(@double)
123
+ scenario = @space.scenario(@double)
124
124
  @space.register_ordered_scenario(scenario)
125
125
 
126
126
  scenario.twice
@@ -131,7 +131,7 @@ describe Space, "#verify_ordered_scenario where the passed in scenario is at the
131
131
  end
132
132
 
133
133
  it "removes the scenario when times called expectation should no longer be attempted" do
134
- scenario = @space.create_scenario(@double)
134
+ scenario = @space.scenario(@double)
135
135
  @space.register_ordered_scenario(scenario)
136
136
 
137
137
  scenario.with(1).once
@@ -147,8 +147,8 @@ describe Space, "#verify_ordered_scenario where the passed in scenario is not at
147
147
  it_should_behave_like "RR::Space#verify_ordered_scenario"
148
148
 
149
149
  it "raises error" do
150
- first_scenario = create_scenario
151
- second_scenario = create_scenario
150
+ first_scenario = scenario
151
+ second_scenario = scenario
152
152
 
153
153
  proc do
154
154
  @space.verify_ordered_scenario(second_scenario)
@@ -160,8 +160,8 @@ describe Space, "#verify_ordered_scenario where the passed in scenario is not at
160
160
  )
161
161
  end
162
162
 
163
- def create_scenario
164
- scenario = @space.create_scenario(@double).once
163
+ def scenario
164
+ scenario = @space.scenario(@double).once
165
165
  @space.register_ordered_scenario(scenario)
166
166
  scenario
167
167
  end
@@ -21,12 +21,21 @@ class TestUnitIntegrationTest < Test::Unit::TestCase
21
21
  assert_equal :baz, @subject.foobar("any", "thing")
22
22
  end
23
23
 
24
- def test_using_a_probe
24
+ def test_using_a_mock_probe
25
25
  def @subject.foobar
26
26
  :baz
27
27
  end
28
28
 
29
- probe(@subject).foobar
29
+ mock.probe(@subject).foobar
30
+ assert_equal :baz, @subject.foobar
31
+ end
32
+
33
+ def test_using_a_stub_probe
34
+ def @subject.foobar
35
+ :baz
36
+ end
37
+
38
+ stub.probe(@subject).foobar
30
39
  assert_equal :baz, @subject.foobar
31
40
  end
32
41
 
data/lib/rr.rb CHANGED
@@ -1,23 +1,21 @@
1
+ require "rr/errors/rr_error"
2
+ require "rr/errors/scenario_definition_error"
3
+ require "rr/errors/scenario_not_found_error"
4
+ require "rr/errors/scenario_order_error"
5
+ require "rr/errors/argument_equality_error"
6
+ require "rr/errors/times_called_error"
7
+
1
8
  require "rr/space"
2
9
  require "rr/double"
3
10
  require "rr/hash_with_object_id_key"
4
11
 
5
- require "rr/creator"
6
- require "rr/mock_creator"
7
- require "rr/stub_creator"
8
- require "rr/mock_probe_creator"
9
- require "rr/stub_probe_creator"
10
- require "rr/do_not_allow_creator"
12
+ require "rr/scenario_method_proxy"
13
+
14
+ require "rr/scenario_creator"
11
15
 
12
16
  require "rr/scenario"
13
17
  require "rr/scenario_matches"
14
18
 
15
- require "rr/errors/rr_error"
16
- require "rr/errors/scenario_not_found_error"
17
- require "rr/errors/scenario_order_error"
18
- require "rr/errors/argument_equality_error"
19
- require "rr/errors/times_called_error"
20
-
21
19
  require "rr/expectations/argument_equality_expectation"
22
20
  require "rr/expectations/any_argument_expectation"
23
21
  require "rr/expectations/times_called_expectation"
@@ -0,0 +1,6 @@
1
+ module RR
2
+ module Errors
3
+ class ScenarioDefinitionError < RRError
4
+ end
5
+ end
6
+ end
@@ -12,57 +12,90 @@ module Extensions
12
12
  RR::Space.instance.reset
13
13
  end
14
14
 
15
- # When passed the object, this method returns a MockCreator
16
- # that generates a Double Scenario that acts like a mock.
17
- # mock(object).method_name_1 {return_value_1}
18
- # mock(object).method_name_2(arg1, arg2) {return_value_2}
19
- #
20
- # When passed the object and the method_name, this method returns
15
+ # This method sets the Scenario to have a mock strategy. A mock strategy
16
+ # sets the default state of the Scenario to expect the method call
17
+ # with arguments exactly one time. The Scenario's expectations can be
18
+ # changed.
19
+ #
20
+ # This method can be chained with probe.
21
+ # mock.probe(subject).method_name_1
22
+ # or
23
+ # probe.mock(subject).method_name_1
24
+ #
25
+ # When passed the subject, a ScenarioMethodProxy is returned. Passing
26
+ # a method with arguments to the proxy will set up expectations that
27
+ # the a call to the subject's method with the arguments will happen,
28
+ # and return the prescribed value.
29
+ # mock(subject).method_name_1 {return_value_1}
30
+ # mock(subject).method_name_2(arg1, arg2) {return_value_2}
31
+ #
32
+ # When passed the subject and the method_name, this method returns
21
33
  # a mock Scenario with the method already set.
22
34
  #
35
+ # mock(subject, :method_name_1) {return_value_1}
36
+ # mock(subject, :method_name_2).with(arg1, arg2) {return_value_2}
37
+ #
23
38
  # mock also takes a block for definitions.
24
- # mock(object) do
39
+ # mock(subject) do
25
40
  # method_name_1 {return_value_1}
26
41
  # method_name_2(arg_1, arg_2) {return_value_2}
27
42
  # end
28
- def mock(object, method_name=nil, &definition)
29
- RR::Space.instance.mock_creator(object, method_name, &definition)
43
+ def mock(subject=ScenarioCreator::NO_SUBJECT_ARG, method_name=nil, &definition)
44
+ creator = RR::Space.scenario_creator
45
+ creator.mock(subject, method_name, &definition)
30
46
  end
31
47
 
32
- # When passed the object, this method returns a StubCreator
33
- # that generates a Double Scenario that acts like a stub.
34
- # stub(object).method_name_1 {return_value_1}
35
- # stub(object).method_name_2(arg_1, arg_2) {return_value_2}
36
- #
37
- # When passed the object and the method_name, this method returns
48
+
49
+ # This method sets the Scenario to have a stub strategy. A stub strategy
50
+ # sets the default state of the Scenario to expect the method call
51
+ # with any arguments any number of times. The Scenario's
52
+ # expectations can be changed.
53
+ #
54
+ # This method can be chained with probe.
55
+ # stub.probe(subject).method_name_1
56
+ # or
57
+ # probe.stub(subject).method_name_1
58
+ #
59
+ # When passed the subject, a ScenarioMethodProxy is returned. Passing
60
+ # a method with arguments to the proxy will set up expectations that
61
+ # the a call to the subject's method with the arguments will happen,
62
+ # and return the prescribed value.
63
+ # stub(subject).method_name_1 {return_value_1}
64
+ # stub(subject).method_name_2(arg_1, arg_2) {return_value_2}
65
+ #
66
+ # When passed the subject and the method_name, this method returns
38
67
  # a stub Scenario with the method already set.
39
68
  #
69
+ # mock(subject, :method_name_1) {return_value_1}
70
+ # mock(subject, :method_name_2).with(arg1, arg2) {return_value_2}
71
+ #
40
72
  # stub also takes a block for definitions.
41
- # stub(object) do
73
+ # stub(subject) do
42
74
  # method_name_1 {return_value_1}
43
75
  # method_name_2(arg_1, arg_2) {return_value_2}
44
76
  # end
45
- def stub(object, method_name=nil, &definition)
46
- RR::Space.instance.stub_creator(object, method_name, &definition)
77
+ def stub(subject=ScenarioCreator::NO_SUBJECT_ARG, method_name=nil, &definition)
78
+ creator = RR::Space.scenario_creator
79
+ creator.stub(subject, method_name, &definition)
47
80
  end
48
81
 
49
- # When passed the object, this method returns a MockProbeCreator
50
- # that generates a Double Scenario that acts like a mock probe.
82
+ # This method add probe capabilities to the Scenario. probe can be called
83
+ # with mock or stub.
51
84
  #
52
- # mock_probe(controller.template).render(:partial => "my/socks")
85
+ # mock.probe(controller.template).render(:partial => "my/socks")
53
86
  #
54
- # mock_probe(controller.template).render(:partial => "my/socks") do |html|
87
+ # stub.probe(controller.template).render(:partial => "my/socks") do |html|
55
88
  # html.should include("My socks are wet")
56
89
  # html
57
90
  # end
58
91
  #
59
- # mock_probe(controller.template).render(:partial => "my/socks") do |html|
92
+ # mock.probe(controller.template).render(:partial => "my/socks") do |html|
60
93
  # html.should include("My socks are wet")
61
94
  # "My new return value"
62
95
  # end
63
96
  #
64
- # mock_probe also takes a block for definitions.
65
- # mock_probe(object) do
97
+ # mock.probe also takes a block for definitions.
98
+ # mock.probe(subject) do
66
99
  # render(:partial => "my/socks")
67
100
  #
68
101
  # render(:partial => "my/socks") do |html|
@@ -87,71 +120,38 @@ module Extensions
87
120
  # passing in a block. The return value of the block will replace
88
121
  # the actual return value.
89
122
  #
90
- # mock_probe(controller.template).render(:partial => "my/socks") do |html|
123
+ # mock.probe(controller.template).render(:partial => "my/socks") do |html|
91
124
  # html.should include("My socks are wet")
92
125
  # "My new return value"
93
126
  # end
94
- def mock_probe(object, method_name=nil, &definition)
95
- RR::Space.instance.mock_probe_creator(object, method_name, &definition)
127
+ def probe(subject=ScenarioCreator::NO_SUBJECT_ARG, method_name=nil, &definition)
128
+ creator = RR::Space.scenario_creator
129
+ creator.probe(subject, method_name, &definition)
96
130
  end
97
131
 
98
- # When passed the object, this method returns a StubProbeCreator
99
- # that generates a Double Scenario that acts like a stub probe.
100
- #
101
- # stub_probe(User).new {|user| user}
102
- #
103
- # stub_probe(User).new do |user|
104
- # mock(user).valid? {false}
105
- # user
106
- # end
107
- #
108
- # stub_probe(User).new do |user|
109
- # mock_probe(user).friends {|friends| friends[0..3]}
110
- # user
111
- # end
112
- #
113
- # Passing a block allows you to intercept the return value.
114
- # The return value can be modified, validated, and/or overridden by
115
- # passing in a block. The return value of the block will replace
116
- # the actual return value.
117
- #
118
- # mock_probe(User) do
119
- # new {|user| user}
120
- #
121
- # new do |user|
122
- # mock(user).valid? {false}
123
- # end
124
- #
125
- # new do |user|
126
- # mock_probe(user).friends {|friends| friends[0..3]}
127
- # user
128
- # end
129
- # end
130
- #
131
- # Passing a block to the Scenario (after the method name and arguments)
132
- # allows you to intercept the return value.
133
- # The return value can be modified, validated, and/or overridden by
134
- # passing in a block. The return value of the block will replace
135
- # the actual return value.
136
- #
137
- # stub_probe(controller.template).render(:partial => "my/socks") do |html|
138
- # html.should include("My socks are wet")
139
- # "My new return value"
140
- # end
141
- def stub_probe(object, method_name=nil, &definition)
142
- RR::Space.instance.stub_probe_creator(object, method_name, &definition)
143
- end
144
-
145
- # Same as mock_probe
146
- alias_method :probe, :mock_probe
147
-
148
- # Sets up a DoNotAllowCreator that generates a Double Scenario that
149
- # expects never to be called.
150
- # do_not_allow(object).method_name
151
- def do_not_allow(subject, method_name=nil, &definition)
152
- RR::Space.instance.do_not_allow_creator(subject, method_name, &definition)
132
+ # This method sets the Scenario to have a do_not_call strategy.
133
+ # A do_not_call strategy sets the default state of the Scenario
134
+ # to expect never to be called. The Scenario's expectations can be
135
+ # changed.
136
+ #
137
+ # The following example sets the expectation that subject.method_name
138
+ # will never be called with arg1 and arg2.
139
+ #
140
+ # do_not_allow(subject).method_name(arg1, arg2)
141
+ #
142
+ # do_not_call also supports a block sytnax.
143
+ # do_not_call(subject) do |m|
144
+ # m.method1 # Do not allow method1 with any arguments
145
+ # m.method2(arg1, arg2) # Do not allow method2 with arguments arg1 and arg2
146
+ # m.method3.with_no_args # Do not allow method3 with no arguments
147
+ # end
148
+ def do_not_call(subject=ScenarioCreator::NO_SUBJECT_ARG, method_name=nil, &definition)
149
+ creator = RR::Space.scenario_creator
150
+ creator.do_not_call(subject, method_name, &definition)
153
151
  end
154
- alias_method :dont_allow, :do_not_allow
152
+ alias_method :dont_call, :do_not_call
153
+ alias_method :do_not_allow, :do_not_call
154
+ alias_method :dont_allow, :do_not_call
155
155
 
156
156
  # Returns a AnyTimesMatcher. This is meant to be passed in as an argument
157
157
  # to Scenario#times.