rr 0.1.0
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/CHANGES +1 -0
- data/README +45 -0
- data/Rakefile +60 -0
- data/examples/environment_fixture_setup.rb +7 -0
- data/examples/example_helper.rb +8 -0
- data/examples/example_suite.rb +45 -0
- data/examples/high_level_example.rb +132 -0
- data/examples/rr/do_not_allow_creator_example.rb +90 -0
- data/examples/rr/double_bind_example.rb +32 -0
- data/examples/rr/double_dispatching_example.rb +167 -0
- data/examples/rr/double_example.rb +67 -0
- data/examples/rr/double_register_scenario_example.rb +25 -0
- data/examples/rr/double_reset_example.rb +60 -0
- data/examples/rr/double_verify_example.rb +24 -0
- data/examples/rr/expectations/any_argument_expectation_example.rb +43 -0
- data/examples/rr/expectations/anything_argument_equality_expectation_example.rb +39 -0
- data/examples/rr/expectations/argument_equality_expectation_example.rb +53 -0
- data/examples/rr/expectations/boolean_argument_equality_expectation_example.rb +49 -0
- data/examples/rr/expectations/duck_type_argument_equality_expectation_example.rb +68 -0
- data/examples/rr/expectations/is_a_argument_equality_expectation_example.rb +51 -0
- data/examples/rr/expectations/numeric_argument_equality_expectation_example.rb +47 -0
- data/examples/rr/expectations/range_argument_equality_expectation_example.rb +60 -0
- data/examples/rr/expectations/regexp_argument_equality_expectation_example.rb +68 -0
- data/examples/rr/expectations/times_called_expectation_example.rb +176 -0
- data/examples/rr/extensions/double_methods_example.rb +130 -0
- data/examples/rr/mock_creator_example.rb +65 -0
- data/examples/rr/probe_creator_example.rb +83 -0
- data/examples/rr/rspec/rspec_adapter_example.rb +64 -0
- data/examples/rr/rspec/rspec_usage_example.rb +38 -0
- data/examples/rr/scenario_example.rb +399 -0
- data/examples/rr/space_create_example.rb +185 -0
- data/examples/rr/space_example.rb +30 -0
- data/examples/rr/space_helper.rb +7 -0
- data/examples/rr/space_register_example.rb +33 -0
- data/examples/rr/space_reset_example.rb +73 -0
- data/examples/rr/space_verify_example.rb +146 -0
- data/examples/rr/stub_creator_example.rb +74 -0
- data/examples/rr/test_unit/test_helper.rb +9 -0
- data/examples/rr/test_unit/test_unit_integration_test.rb +39 -0
- data/examples/rspec_example_suite.rb +25 -0
- data/examples/test_unit_example_suite.rb +21 -0
- data/lib/rr.rb +27 -0
- data/lib/rr/adapters/rspec.rb +19 -0
- data/lib/rr/adapters/test_unit.rb +27 -0
- data/lib/rr/do_not_allow_creator.rb +39 -0
- data/lib/rr/double.rb +91 -0
- data/lib/rr/expectations/any_argument_expectation.rb +17 -0
- data/lib/rr/expectations/argument_equality_expectation.rb +35 -0
- data/lib/rr/expectations/times_called_expectation.rb +39 -0
- data/lib/rr/expectations/wildcard_matchers/anything.rb +15 -0
- data/lib/rr/expectations/wildcard_matchers/boolean.rb +20 -0
- data/lib/rr/expectations/wildcard_matchers/duck_type.rb +26 -0
- data/lib/rr/expectations/wildcard_matchers/is_a.rb +22 -0
- data/lib/rr/expectations/wildcard_matchers/numeric.rb +11 -0
- data/lib/rr/expectations/wildcard_matchers/range.rb +7 -0
- data/lib/rr/expectations/wildcard_matchers/regexp.rb +7 -0
- data/lib/rr/extensions/double_methods.rb +81 -0
- data/lib/rr/mock_creator.rb +32 -0
- data/lib/rr/probe_creator.rb +31 -0
- data/lib/rr/scenario.rb +184 -0
- data/lib/rr/scenario_not_found_error.rb +4 -0
- data/lib/rr/scenario_order_error.rb +4 -0
- data/lib/rr/space.rb +111 -0
- data/lib/rr/stub_creator.rb +36 -0
- metadata +113 -0
data/CHANGES
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
* 0.1.0
|
data/README
ADDED
@@ -0,0 +1,45 @@
|
|
1
|
+
= RR
|
2
|
+
|
3
|
+
RR (Double Ruby) is a double framework that features a rich
|
4
|
+
selection of double techniques and a terse syntax.
|
5
|
+
http://xunitpatterns.com/Test%20Double.html
|
6
|
+
|
7
|
+
Currently RR implements mocks, stubs, and probes. It is a goal of
|
8
|
+
RR to support a wide range of double techniques and patterns.
|
9
|
+
|
10
|
+
== Mocking
|
11
|
+
http://xunitpatterns.com/Mock%20Object.html
|
12
|
+
view = controller.template
|
13
|
+
mock(view).render(:partial => "user_info") {"Information"}
|
14
|
+
|
15
|
+
== Stubbing
|
16
|
+
http://xunitpatterns.com/Test%20Stub.html
|
17
|
+
jane = User.new
|
18
|
+
stub(User).find('42') {jane}
|
19
|
+
mock(jane).valid? {true}
|
20
|
+
|
21
|
+
== Probing
|
22
|
+
Add verifications that a method was called while actually calling it.
|
23
|
+
The following example verifies render partial will be called and
|
24
|
+
renders the partial.
|
25
|
+
|
26
|
+
view = controller.template
|
27
|
+
probe(view).render(:partial => "user_info")
|
28
|
+
|
29
|
+
== Block Syntax
|
30
|
+
script = MyScript.new
|
31
|
+
mock(script) do |m|
|
32
|
+
m.system("cd #{RAILS_ENV}") {true}
|
33
|
+
m.system("rake foo:bar") {true}
|
34
|
+
m.system("rake baz") {true}
|
35
|
+
end
|
36
|
+
|
37
|
+
== Terse Syntax
|
38
|
+
One of the goals of RR is to make doubles more scannable.
|
39
|
+
This is accomplished by removing words from a double declaration.
|
40
|
+
Here is RR compared to other mock frameworks:
|
41
|
+
|
42
|
+
flexmock(User).should_receive(:find).with('42').and_return(jane) # Flexmock
|
43
|
+
User.should_receive(:find).with('42').and_return(jane) # Rspec
|
44
|
+
User.expects(:find).with('42').returns {jane} # Mocha
|
45
|
+
mock(User).find('42') {jane} # RR
|
data/Rakefile
ADDED
@@ -0,0 +1,60 @@
|
|
1
|
+
require "rake"
|
2
|
+
require 'rake/gempackagetask'
|
3
|
+
require 'rake/contrib/rubyforgepublisher'
|
4
|
+
require 'rake/clean'
|
5
|
+
require 'rake/testtask'
|
6
|
+
require 'rake/rdoctask'
|
7
|
+
|
8
|
+
desc "Runs the Rspec suite"
|
9
|
+
task(:default) do
|
10
|
+
run_suite
|
11
|
+
end
|
12
|
+
|
13
|
+
desc "Runs the Rspec suite"
|
14
|
+
task(:spec) do
|
15
|
+
run_suite
|
16
|
+
end
|
17
|
+
|
18
|
+
def run_suite
|
19
|
+
dir = File.dirname(__FILE__)
|
20
|
+
system("ruby #{dir}/examples/example_suite.rb") || raise("Example Suite failed")
|
21
|
+
end
|
22
|
+
|
23
|
+
PKG_NAME = "rr"
|
24
|
+
PKG_VERSION = "0.1.0"
|
25
|
+
PKG_FILES = FileList[
|
26
|
+
'[A-Z]*',
|
27
|
+
'*.rb',
|
28
|
+
'lib/**/*.rb',
|
29
|
+
'examples/**/*.rb'
|
30
|
+
]
|
31
|
+
|
32
|
+
spec = Gem::Specification.new do |s|
|
33
|
+
s.name = PKG_NAME
|
34
|
+
s.version = PKG_VERSION
|
35
|
+
s.summary = "RR (Double Ruby) is a double framework that features a rich " <<
|
36
|
+
"selection of double techniques and a terse syntax. " <<
|
37
|
+
"http://xunitpatterns.com/Test%20Double.html"
|
38
|
+
s.test_files = "examples/example_suite.rb"
|
39
|
+
s.description = s.summary
|
40
|
+
|
41
|
+
s.files = PKG_FILES.to_a
|
42
|
+
s.require_path = 'lib'
|
43
|
+
|
44
|
+
s.has_rdoc = true
|
45
|
+
s.extra_rdoc_files = [ "README", "CHANGES" ]
|
46
|
+
s.rdoc_options = ["--main", "README", "--inline-source", "--line-numbers"]
|
47
|
+
|
48
|
+
s.test_files = Dir.glob('spec/*_spec.rb')
|
49
|
+
s.require_path = 'lib'
|
50
|
+
s.autorequire = 'rr'
|
51
|
+
s.author = "Brian Takita"
|
52
|
+
s.email = "brian@pivotallabs.com"
|
53
|
+
s.homepage = "http://pivotallabs.com"
|
54
|
+
s.rubyforge_project = "pivotalrb"
|
55
|
+
end
|
56
|
+
|
57
|
+
Rake::GemPackageTask.new(spec) do |pkg|
|
58
|
+
pkg.need_zip = true
|
59
|
+
pkg.need_tar = true
|
60
|
+
end
|
@@ -0,0 +1,45 @@
|
|
1
|
+
require "rubygems"
|
2
|
+
require "spec"
|
3
|
+
|
4
|
+
class ExampleSuite
|
5
|
+
def run
|
6
|
+
options = ::Spec::Runner::OptionParser.new.parse(ARGV.dup, STDERR, STDOUT, false)
|
7
|
+
$behaviour_runner = options.create_behaviour_runner
|
8
|
+
|
9
|
+
require_specs
|
10
|
+
|
11
|
+
puts "Running Example Suite"
|
12
|
+
$behaviour_runner.run(ARGV, false)
|
13
|
+
|
14
|
+
run_rspec_examples
|
15
|
+
run_test_unit_examples
|
16
|
+
end
|
17
|
+
|
18
|
+
def require_specs
|
19
|
+
exclusions = []
|
20
|
+
exclusions << "rspec/"
|
21
|
+
exclusions << "test_unit/"
|
22
|
+
|
23
|
+
Dir["#{dir}/**/*_example.rb"].each do |file|
|
24
|
+
unless exclusions.any? {|match| file.include?(match)}
|
25
|
+
require file
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
29
|
+
|
30
|
+
def run_rspec_examples
|
31
|
+
system("ruby #{dir}/rspec_example_suite.rb") || raise("Rspec suite Failed")
|
32
|
+
end
|
33
|
+
|
34
|
+
def run_test_unit_examples
|
35
|
+
system("ruby #{dir}/test_unit_example_suite.rb") || raise("Test::Unit suite Failed")
|
36
|
+
end
|
37
|
+
|
38
|
+
def dir
|
39
|
+
File.dirname(__FILE__)
|
40
|
+
end
|
41
|
+
end
|
42
|
+
|
43
|
+
if $0 == __FILE__
|
44
|
+
ExampleSuite.new.run
|
45
|
+
end
|
@@ -0,0 +1,132 @@
|
|
1
|
+
dir = File.dirname(__FILE__)
|
2
|
+
require "#{dir}/example_helper"
|
3
|
+
|
4
|
+
describe "RR", :shared => true do
|
5
|
+
before(:each) do
|
6
|
+
@obj = Object.new
|
7
|
+
extend RR::Extensions::DoubleMethods
|
8
|
+
end
|
9
|
+
|
10
|
+
after(:each) do
|
11
|
+
RR::Space.instance.reset_doubles
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
describe "RR mock:" do
|
16
|
+
it_should_behave_like "RR"
|
17
|
+
|
18
|
+
it "mocks via inline call" do
|
19
|
+
mock(@obj).to_s {"a value"}
|
20
|
+
@obj.to_s.should == "a value"
|
21
|
+
proc {@obj.to_s}.should raise_error(RR::Expectations::TimesCalledExpectationError)
|
22
|
+
end
|
23
|
+
|
24
|
+
it "allows ordering" do
|
25
|
+
mock(@obj).to_s {"value 1"}.ordered
|
26
|
+
mock(@obj).to_s {"value 2"}.twice.ordered
|
27
|
+
@obj.to_s.should == "value 1"
|
28
|
+
@obj.to_s.should == "value 2"
|
29
|
+
@obj.to_s.should == "value 2"
|
30
|
+
proc {@obj.to_s}.should raise_error(RR::Expectations::TimesCalledExpectationError)
|
31
|
+
end
|
32
|
+
|
33
|
+
it "mocks via block" do
|
34
|
+
mock @obj do |c|
|
35
|
+
c.to_s {"a value"}
|
36
|
+
c.to_sym {:crazy}
|
37
|
+
end
|
38
|
+
@obj.to_s.should == "a value"
|
39
|
+
@obj.to_sym.should == :crazy
|
40
|
+
end
|
41
|
+
|
42
|
+
it "has wildcard matchers" do
|
43
|
+
mock(@obj).foobar(
|
44
|
+
is_a(String),
|
45
|
+
anything,
|
46
|
+
numeric,
|
47
|
+
boolean,
|
48
|
+
duck_type(:to_s),
|
49
|
+
/abc/
|
50
|
+
) {"value 1"}.twice
|
51
|
+
@obj.foobar(
|
52
|
+
'hello',
|
53
|
+
Object.new,
|
54
|
+
99,
|
55
|
+
false,
|
56
|
+
"My String",
|
57
|
+
"Tabcola"
|
58
|
+
).should == "value 1"
|
59
|
+
proc {@obj.foobar(:failure)}.should raise_error( RR::ScenarioNotFoundError )
|
60
|
+
end
|
61
|
+
end
|
62
|
+
|
63
|
+
describe "RR probe:" do
|
64
|
+
it_should_behave_like "RR"
|
65
|
+
|
66
|
+
it "probes via inline call" do
|
67
|
+
expected_to_s_value = @obj.to_s
|
68
|
+
probe(@obj).to_s
|
69
|
+
@obj.to_s.should == expected_to_s_value
|
70
|
+
proc {@obj.to_s}.should raise_error
|
71
|
+
end
|
72
|
+
|
73
|
+
it "allows ordering" do
|
74
|
+
def @obj.to_s(arg)
|
75
|
+
"Original to_s with arg #{arg}"
|
76
|
+
end
|
77
|
+
probe(@obj).to_s(:foo).ordered
|
78
|
+
probe(@obj).to_s(:bar).twice.ordered
|
79
|
+
|
80
|
+
@obj.to_s(:foo).should == "Original to_s with arg foo"
|
81
|
+
@obj.to_s(:bar).should == "Original to_s with arg bar"
|
82
|
+
@obj.to_s(:bar).should == "Original to_s with arg bar"
|
83
|
+
proc {@obj.to_s(:bar)}.should raise_error(RR::Expectations::TimesCalledExpectationError)
|
84
|
+
end
|
85
|
+
|
86
|
+
it "probes via block" do
|
87
|
+
def @obj.foobar_1(*args)
|
88
|
+
:original_value_1
|
89
|
+
end
|
90
|
+
|
91
|
+
def @obj.foobar_2
|
92
|
+
:original_value_2
|
93
|
+
end
|
94
|
+
|
95
|
+
probe @obj do |c|
|
96
|
+
c.foobar_1(1)
|
97
|
+
c.foobar_2
|
98
|
+
end
|
99
|
+
@obj.foobar_1(1).should == :original_value_1
|
100
|
+
proc {@obj.foobar_1(:blah)}.should raise_error
|
101
|
+
|
102
|
+
@obj.foobar_2.should == :original_value_2
|
103
|
+
proc {@obj.foobar_2(:blah)}.should raise_error
|
104
|
+
end
|
105
|
+
end
|
106
|
+
|
107
|
+
describe "RR stub:" do
|
108
|
+
it_should_behave_like "RR"
|
109
|
+
|
110
|
+
it "stubs via inline call" do
|
111
|
+
stub(@obj).to_s {"a value"}
|
112
|
+
@obj.to_s.should == "a value"
|
113
|
+
end
|
114
|
+
|
115
|
+
it "allows ordering" do
|
116
|
+
stub(@obj).to_s {"value 1"}.once.ordered
|
117
|
+
|
118
|
+
stub(@obj).to_s {"value 2"}.once.ordered
|
119
|
+
|
120
|
+
@obj.to_s.should == "value 1"
|
121
|
+
@obj.to_s.should == "value 2"
|
122
|
+
end
|
123
|
+
|
124
|
+
it "stubs via block" do
|
125
|
+
stub @obj do |d|
|
126
|
+
d.to_s {"a value"}
|
127
|
+
d.to_sym {:crazy}
|
128
|
+
end
|
129
|
+
@obj.to_s.should == "a value"
|
130
|
+
@obj.to_sym.should == :crazy
|
131
|
+
end
|
132
|
+
end
|
@@ -0,0 +1,90 @@
|
|
1
|
+
dir = File.dirname(__FILE__)
|
2
|
+
require "#{dir}/../example_helper"
|
3
|
+
|
4
|
+
module RR
|
5
|
+
describe DoNotAllowCreator, :shared => true do
|
6
|
+
before(:each) do
|
7
|
+
@space = Space.new
|
8
|
+
@subject = Object.new
|
9
|
+
end
|
10
|
+
|
11
|
+
it "initializes creator with passed in object" do
|
12
|
+
class << @creator
|
13
|
+
attr_reader :subject
|
14
|
+
end
|
15
|
+
@creator.subject.should === @subject
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
describe DoNotAllowCreator, ".new" do
|
20
|
+
it_should_behave_like "RR::DoNotAllowCreator"
|
21
|
+
|
22
|
+
before do
|
23
|
+
@creator = DoNotAllowCreator.new(@space, @subject)
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
describe DoNotAllowCreator, ".new with block" do
|
28
|
+
it_should_behave_like "RR::DoNotAllowCreator"
|
29
|
+
|
30
|
+
before do
|
31
|
+
@creator = DoNotAllowCreator.new(@space, @subject) do |c|
|
32
|
+
c.any_args
|
33
|
+
c.no_args.with_no_args
|
34
|
+
c.with_args(1, 2)
|
35
|
+
end
|
36
|
+
end
|
37
|
+
|
38
|
+
it "raises TimesCalledExpectationError when any_args is called with no arguments" do
|
39
|
+
proc {@subject.any_args}.should raise_error(Expectations::TimesCalledExpectationError)
|
40
|
+
end
|
41
|
+
|
42
|
+
it "raises TimesCalledExpectationError when any_args is called with arguments" do
|
43
|
+
proc {@subject.any_args(1, 2)}.should raise_error(Expectations::TimesCalledExpectationError)
|
44
|
+
end
|
45
|
+
|
46
|
+
it "raises TimesCalledExpectationError when no_args is called with no arguments" do
|
47
|
+
proc {@subject.no_args}.should raise_error(Expectations::TimesCalledExpectationError)
|
48
|
+
end
|
49
|
+
|
50
|
+
it "does not raise TimesCalledExpectationError when no_args is called with arguments" do
|
51
|
+
proc {@subject.no_args(1, 2)}.should raise_error(ScenarioNotFoundError)
|
52
|
+
end
|
53
|
+
|
54
|
+
it "raises TimesCalledExpectationError when any_args is called with no arguments" do
|
55
|
+
proc {@subject.with_args}.should raise_error(ScenarioNotFoundError)
|
56
|
+
end
|
57
|
+
|
58
|
+
it "raises TimesCalledExpectationError when any_args is called with arguments" do
|
59
|
+
proc {@subject.any_args(1, 2)}.should raise_error(Expectations::TimesCalledExpectationError)
|
60
|
+
end
|
61
|
+
end
|
62
|
+
|
63
|
+
describe DoNotAllowCreator, "#method_missing" do
|
64
|
+
it_should_behave_like "RR::DoNotAllowCreator"
|
65
|
+
|
66
|
+
before do
|
67
|
+
@subject = Object.new
|
68
|
+
@creator = DoNotAllowCreator.new(@space, @subject)
|
69
|
+
end
|
70
|
+
|
71
|
+
it "sets expectation for method to never be called with any arguments when on arguments passed in" do
|
72
|
+
@creator.foobar
|
73
|
+
proc {@subject.foobar}.should raise_error(Expectations::TimesCalledExpectationError)
|
74
|
+
proc {@subject.foobar(1, 2)}.should raise_error(Expectations::TimesCalledExpectationError)
|
75
|
+
end
|
76
|
+
|
77
|
+
it "sets expectation for method to never be called with passed in arguments" do
|
78
|
+
@creator.foobar(1, 2)
|
79
|
+
proc {@subject.foobar}.should raise_error(ScenarioNotFoundError)
|
80
|
+
proc {@subject.foobar(1, 2)}.should raise_error(Expectations::TimesCalledExpectationError)
|
81
|
+
end
|
82
|
+
|
83
|
+
it "sets expectation for method to never be called with no arguments when with_no_args is set" do
|
84
|
+
@creator.foobar.with_no_args
|
85
|
+
proc {@subject.foobar}.should raise_error(Expectations::TimesCalledExpectationError)
|
86
|
+
proc {@subject.foobar(1, 2)}.should raise_error(ScenarioNotFoundError)
|
87
|
+
end
|
88
|
+
end
|
89
|
+
|
90
|
+
end
|
@@ -0,0 +1,32 @@
|
|
1
|
+
dir = File.dirname(__FILE__)
|
2
|
+
require "#{dir}/../example_helper"
|
3
|
+
|
4
|
+
module RR
|
5
|
+
describe Double, "#bind with an existing method" do
|
6
|
+
before do
|
7
|
+
@space = Space.new
|
8
|
+
@object = Object.new
|
9
|
+
@method_name = :foobar
|
10
|
+
def @object.foobar; :original_foobar; end
|
11
|
+
@object.methods.should include(@method_name.to_s)
|
12
|
+
@double = Double.new(@space, @object, @method_name)
|
13
|
+
end
|
14
|
+
|
15
|
+
it "overrides the original method with the double's dispatching methods" do
|
16
|
+
@object.respond_to?(:__rr__foobar__rr__).should == false
|
17
|
+
@double.bind
|
18
|
+
@object.respond_to?(:__rr__foobar__rr__).should == true
|
19
|
+
|
20
|
+
rr_foobar_called = false
|
21
|
+
(class << @object; self; end).class_eval do
|
22
|
+
define_method :__rr__foobar__rr__ do
|
23
|
+
rr_foobar_called = true
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
rr_foobar_called.should == false
|
28
|
+
@object.foobar
|
29
|
+
rr_foobar_called.should == true
|
30
|
+
end
|
31
|
+
end
|
32
|
+
end
|
@@ -0,0 +1,167 @@
|
|
1
|
+
dir = File.dirname(__FILE__)
|
2
|
+
require "#{dir}/../example_helper"
|
3
|
+
|
4
|
+
module RR
|
5
|
+
describe Double, "method dispatching", :shared => true do
|
6
|
+
before do
|
7
|
+
@space = Space.new
|
8
|
+
@object = Object.new
|
9
|
+
@method_name = :foobar
|
10
|
+
@object.methods.should_not include(@method_name.to_s)
|
11
|
+
@double = @space.create_double(@object, @method_name)
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
describe Double, " method dispatching where the scenario takes a block" do
|
16
|
+
it_should_behave_like "RR::Double method dispatching"
|
17
|
+
|
18
|
+
it "executes the block" do
|
19
|
+
method_fixture = Object.new
|
20
|
+
class << method_fixture
|
21
|
+
def method_with_block(a, b)
|
22
|
+
yield(a,b)
|
23
|
+
end
|
24
|
+
end
|
25
|
+
scenario = @space.create_scenario(@double)
|
26
|
+
scenario.with(1, 2).implemented_by(method_fixture.method(:method_with_block))
|
27
|
+
@object.foobar(1, 2) {|a, b| [b, a]}.should == [2, 1]
|
28
|
+
end
|
29
|
+
end
|
30
|
+
|
31
|
+
describe Double, " method dispatching where there are no scenarios with duplicate ArgumentExpectations" do
|
32
|
+
it_should_behave_like "RR::Double method dispatching"
|
33
|
+
|
34
|
+
it "dispatches to Scenario that have an exact match" do
|
35
|
+
scenario1_with_exact_match = @space.create_scenario(@double)
|
36
|
+
scenario1_with_exact_match.with(:exact_match_1).returns {:return_1}
|
37
|
+
scenario_with_no_match = @space.create_scenario(@double)
|
38
|
+
scenario_with_no_match.with("nothing that matches").returns {:no_match}
|
39
|
+
scenario2_with_exact_match = @space.create_scenario(@double)
|
40
|
+
scenario2_with_exact_match.with(:exact_match_2).returns {:return_2}
|
41
|
+
|
42
|
+
@object.foobar(:exact_match_1).should == :return_1
|
43
|
+
@object.foobar(:exact_match_2).should == :return_2
|
44
|
+
end
|
45
|
+
|
46
|
+
it "dispatches to Scenario that have a wildcard match" do
|
47
|
+
scenario_with_wildcard_match = @space.create_scenario(@double)
|
48
|
+
scenario_with_wildcard_match.with_any_args.returns {:wild_card_value}
|
49
|
+
scenario_with_no_match = @space.create_scenario(@double)
|
50
|
+
scenario_with_no_match.with("nothing that matches").returns {:no_match}
|
51
|
+
|
52
|
+
@object.foobar(:wildcard_match_1).should == :wild_card_value
|
53
|
+
@object.foobar(:wildcard_match_2, 3).should == :wild_card_value
|
54
|
+
end
|
55
|
+
end
|
56
|
+
|
57
|
+
describe Double, " method dispatching where there are scenarios" do
|
58
|
+
it_should_behave_like "RR::Double method dispatching"
|
59
|
+
|
60
|
+
it "raises ScenarioNotFoundError error when arguments do not match a scenario" do
|
61
|
+
scenario_1 = @space.create_scenario(@double)
|
62
|
+
scenario_1.with(1, 2)
|
63
|
+
|
64
|
+
scenario_2 = @space.create_scenario(@double)
|
65
|
+
scenario_2.with(3)
|
66
|
+
|
67
|
+
proc {@object.foobar(:no_matching_args)}.should raise_error(
|
68
|
+
ScenarioNotFoundError,
|
69
|
+
"No scenario for arguments [:no_matching_args]"
|
70
|
+
)
|
71
|
+
end
|
72
|
+
end
|
73
|
+
|
74
|
+
describe Double, " method dispatching where there are scenarios with duplicate Exact Match ArgumentExpectations" do
|
75
|
+
it_should_behave_like "RR::Double method dispatching"
|
76
|
+
|
77
|
+
it "dispatches to Scenario that have an exact match" do
|
78
|
+
scenario1_with_exact_match = @space.create_scenario(@double)
|
79
|
+
scenario1_with_exact_match.with(:exact_match).returns {:return_1}
|
80
|
+
|
81
|
+
@object.foobar(:exact_match).should == :return_1
|
82
|
+
end
|
83
|
+
|
84
|
+
it "dispatches to the first Scenario that have an exact match" do
|
85
|
+
scenario1_with_exact_match = @space.create_scenario(@double)
|
86
|
+
scenario1_with_exact_match.with(:exact_match).returns {:return_1}
|
87
|
+
|
88
|
+
scenario2_with_exact_match = @space.create_scenario(@double)
|
89
|
+
scenario2_with_exact_match.with(:exact_match).returns {:return_2}
|
90
|
+
|
91
|
+
@object.foobar(:exact_match).should == :return_1
|
92
|
+
end
|
93
|
+
|
94
|
+
it "dispatches the second Scenario with an exact match
|
95
|
+
when the first scenario's Times Called expectation is satisfied" do
|
96
|
+
scenario1_with_exact_match = @space.create_scenario(@double)
|
97
|
+
scenario1_with_exact_match.with(:exact_match).returns {:return_1}.once
|
98
|
+
|
99
|
+
scenario2_with_exact_match = @space.create_scenario(@double)
|
100
|
+
scenario2_with_exact_match.with(:exact_match).returns {:return_2}.once
|
101
|
+
|
102
|
+
@object.foobar(:exact_match)
|
103
|
+
@object.foobar(:exact_match).should == :return_2
|
104
|
+
end
|
105
|
+
|
106
|
+
it "raises TimesCalledExpectationError when all of the scenarios Times Called expectation is satisfied" do
|
107
|
+
scenario1_with_exact_match = @space.create_scenario(@double)
|
108
|
+
scenario1_with_exact_match.with(:exact_match).returns {:return_1}.once
|
109
|
+
|
110
|
+
scenario2_with_exact_match = @space.create_scenario(@double)
|
111
|
+
scenario2_with_exact_match.with(:exact_match).returns {:return_2}.once
|
112
|
+
|
113
|
+
@object.foobar(:exact_match)
|
114
|
+
@object.foobar(:exact_match)
|
115
|
+
proc do
|
116
|
+
@object.foobar(:exact_match)
|
117
|
+
end.should raise_error(Expectations::TimesCalledExpectationError)
|
118
|
+
end
|
119
|
+
end
|
120
|
+
|
121
|
+
describe Double, " method dispatching where there are scenarios with duplicate Wildcard Match ArgumentExpectations" do
|
122
|
+
it_should_behave_like "RR::Double method dispatching"
|
123
|
+
|
124
|
+
it "dispatches to Scenario that have a wildcard match" do
|
125
|
+
scenario_1 = @space.create_scenario(@double)
|
126
|
+
scenario_1.with_any_args.returns {:return_1}
|
127
|
+
|
128
|
+
@object.foobar(:anything).should == :return_1
|
129
|
+
end
|
130
|
+
|
131
|
+
it "dispatches to the first Scenario that has a wildcard match" do
|
132
|
+
scenario_1 = @space.create_scenario(@double)
|
133
|
+
scenario_1.with_any_args.returns {:return_1}
|
134
|
+
|
135
|
+
scenario_2 = @space.create_scenario(@double)
|
136
|
+
scenario_2.with_any_args.returns {:return_2}
|
137
|
+
|
138
|
+
@object.foobar(:anything).should == :return_1
|
139
|
+
end
|
140
|
+
|
141
|
+
it "dispatches the second Scenario with a wildcard match
|
142
|
+
when the first scenario's Times Called expectation is satisfied" do
|
143
|
+
scenario_1 = @space.create_scenario(@double)
|
144
|
+
scenario_1.with_any_args.returns {:return_1}.once
|
145
|
+
|
146
|
+
scenario_2 = @space.create_scenario(@double)
|
147
|
+
scenario_2.with_any_args.returns {:return_2}.once
|
148
|
+
|
149
|
+
@object.foobar(:anything)
|
150
|
+
@object.foobar(:anything).should == :return_2
|
151
|
+
end
|
152
|
+
|
153
|
+
it "raises TimesCalledExpectationError when all of the scenarios Times Called expectation is satisfied" do
|
154
|
+
scenario_1 = @space.create_scenario(@double)
|
155
|
+
scenario_1.with_any_args.returns {:return_1}.once
|
156
|
+
|
157
|
+
scenario_2 = @space.create_scenario(@double)
|
158
|
+
scenario_2.with_any_args.returns {:return_2}.once
|
159
|
+
|
160
|
+
@object.foobar(:anything)
|
161
|
+
@object.foobar(:anything)
|
162
|
+
proc do
|
163
|
+
@object.foobar(:anything)
|
164
|
+
end.should raise_error(Expectations::TimesCalledExpectationError)
|
165
|
+
end
|
166
|
+
end
|
167
|
+
end
|