cross-stub 0.1.4 → 0.2.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/HISTORY.txt +12 -0
- data/README.rdoc +85 -29
- data/Rakefile +8 -1
- data/VERSION +1 -1
- data/cross-stub.gemspec +37 -19
- data/lib/cross-stub.rb +63 -24
- data/lib/cross-stub/arguments.rb +21 -0
- data/lib/cross-stub/arguments/array.rb +16 -0
- data/lib/cross-stub/arguments/hash.rb +17 -0
- data/lib/cross-stub/arguments/proc.rb +73 -0
- data/lib/cross-stub/cache.rb +36 -0
- data/lib/cross-stub/stores.rb +4 -0
- data/lib/cross-stub/stores/base.rb +38 -0
- data/lib/cross-stub/stores/file.rb +39 -0
- data/lib/cross-stub/stores/memcache.rb +40 -0
- data/lib/cross-stub/stores/redis.rb +41 -0
- data/lib/cross-stub/stubber.rb +132 -0
- data/rails_generators/cross_stub/cross_stub_generator.rb +1 -1
- data/rails_generators/cross_stub/templates/config/initializers/cross-stub.rb +9 -1
- data/rails_generators/cross_stub/templates/features/support/cross-stub.rb +16 -2
- data/spec/arguments/proc_spec.rb +689 -0
- data/spec/includes.rb +103 -0
- data/spec/integration/clearing_instance_stubs_spec.rb +119 -0
- data/spec/integration/clearing_stubs_spec.rb +118 -0
- data/spec/integration/creating_instance_stubs_spec.rb +91 -0
- data/spec/integration/creating_stubs_spec.rb +95 -0
- data/spec/integration/shared_spec.rb +35 -0
- data/spec/integration/stubbing_error_spec.rb +69 -0
- data/spec/service.rb +114 -0
- data/spec/spec_helper.rb +1 -41
- metadata +58 -26
- data/lib/cross-stub/cache_helpers.rb +0 -48
- data/lib/cross-stub/pseudo_class.rb +0 -82
- data/lib/cross-stub/setup_helpers.rb +0 -13
- data/lib/cross-stub/stub_helpers.rb +0 -64
- data/spec/cross-stub/clearing_stubs_spec.rb +0 -112
- data/spec/cross-stub/creating_stubs_spec.rb +0 -110
- data/spec/cross-stub/stubbing_error_spec.rb +0 -38
- data/spec/helpers.rb +0 -125
data/spec/includes.rb
ADDED
@@ -0,0 +1,103 @@
|
|
1
|
+
unless Object.const_defined?(:RUBY_VM)
|
2
|
+
|
3
|
+
# ///////////////////////////////////////////////////////////////////////
|
4
|
+
# Constants
|
5
|
+
# ///////////////////////////////////////////////////////////////////////
|
6
|
+
|
7
|
+
RUBY_VM = [
|
8
|
+
RUBY_VERSION.gsub(/[^\d]/,''),
|
9
|
+
RUBY_PLATFORM =~ /java/i ? 'j' : '',
|
10
|
+
RUBY_DESCRIPTION =~ /enterprise/i ? 'e' : ''
|
11
|
+
].join
|
12
|
+
|
13
|
+
PROJECT_ROOT = File.join(File.dirname(__FILE__), '..')
|
14
|
+
PROJECT_FILE = lambda{|*args| File.join(*[PROJECT_ROOT, *args]) }
|
15
|
+
|
16
|
+
CACHE_STORES = {
|
17
|
+
:file => PROJECT_FILE['tmp', "stubbing-#{RUBY_VM}.cache"],
|
18
|
+
:memcache => "localhost:11211/stubbing-#{RUBY_VM}.cache",
|
19
|
+
:redis => "localhost:6379/stubbing-#{RUBY_VM}.cache",
|
20
|
+
}
|
21
|
+
|
22
|
+
ECHO_SERVER_INIT_WAIT_TIME = RUBY_VM.end_with?('j') ? 10 : 2
|
23
|
+
ECHO_SERVER_LOG = PROJECT_FILE['tmp', "echoserver-#{RUBY_VM}.log"]
|
24
|
+
ECHO_SERVER_HOST = '127.0.0.1'
|
25
|
+
ECHO_SERVER_PORT = 10000 + RUBY_VM[/(\d+)/,1].to_i + ({'j' => 7, 'e' => 17}[RUBY_VM[-1..-1]] || 0)
|
26
|
+
|
27
|
+
# /////////////////////////////////////////////////////////////////////////////////////////
|
28
|
+
# Useful methods
|
29
|
+
# /////////////////////////////////////////////////////////////////////////////////////////
|
30
|
+
|
31
|
+
def cache_store(id)
|
32
|
+
{(id = :"#{id}") => CACHE_STORES[id]}
|
33
|
+
end
|
34
|
+
|
35
|
+
def each_cache_store(&block)
|
36
|
+
CACHE_STORES.keys.each do |store_type|
|
37
|
+
yield(store_type)
|
38
|
+
end
|
39
|
+
end
|
40
|
+
|
41
|
+
def do_local_method_call(klass_and_method_and_args)
|
42
|
+
klass, is_instance, method, args = parse_call_args(klass_and_method_and_args)
|
43
|
+
receiver = is_instance ? klass.new : klass
|
44
|
+
args.empty? ? receiver.send(method) : receiver.send(method, *args)
|
45
|
+
end
|
46
|
+
|
47
|
+
def parse_call_args(klass_and_method_and_args)
|
48
|
+
klass_descriptor, method, *args = klass_and_method_and_args.split('.')
|
49
|
+
is_instance = klass_descriptor.end_with?(suffix = '#new')
|
50
|
+
[klassify(klass_descriptor), is_instance, method, args]
|
51
|
+
end
|
52
|
+
|
53
|
+
def do_remote_method_call(store_type_and_klass_and_method_and_args)
|
54
|
+
(value = EchoClient.get(store_type_and_klass_and_method_and_args)) !~ /^undefined method/ ?
|
55
|
+
value : Object.we_just_wanna_trigger_no_method_error_with_this_weird_method!
|
56
|
+
end
|
57
|
+
|
58
|
+
def klassify(descriptor)
|
59
|
+
descriptor.sub('#new','').split(/::/).inject(Object){|k,c| k.const_get(c) }
|
60
|
+
end
|
61
|
+
|
62
|
+
# /////////////////////////////////////////////////////////////////////////////////////////
|
63
|
+
# Loading of files
|
64
|
+
# /////////////////////////////////////////////////////////////////////////////////////////
|
65
|
+
|
66
|
+
$LOAD_PATH.unshift(PROJECT_FILE['lib'])
|
67
|
+
require 'cross-stub'
|
68
|
+
|
69
|
+
# /////////////////////////////////////////////////////////////////////////////////////////
|
70
|
+
# Class definitions for specs
|
71
|
+
# /////////////////////////////////////////////////////////////////////////////////////////
|
72
|
+
|
73
|
+
class AnyClass
|
74
|
+
|
75
|
+
def self.say ; 'hello' ; end
|
76
|
+
|
77
|
+
class Inner
|
78
|
+
def self.say ; 'hello' ; end
|
79
|
+
end
|
80
|
+
|
81
|
+
end
|
82
|
+
|
83
|
+
class AnyInstance
|
84
|
+
|
85
|
+
def say ; 'hello' ; end
|
86
|
+
|
87
|
+
class Inner
|
88
|
+
def say ; 'hello' ; end
|
89
|
+
end
|
90
|
+
|
91
|
+
end
|
92
|
+
|
93
|
+
module AnyModule
|
94
|
+
|
95
|
+
def self.say ; 'hello' ; end
|
96
|
+
|
97
|
+
module Inner
|
98
|
+
def self.say ; 'hello' ; end
|
99
|
+
end
|
100
|
+
|
101
|
+
end
|
102
|
+
|
103
|
+
end
|
@@ -0,0 +1,119 @@
|
|
1
|
+
require File.join(File.dirname(__FILE__), 'shared_spec')
|
2
|
+
|
3
|
+
describe 'Clearing Instance Stubs' do
|
4
|
+
|
5
|
+
each_cache_store do |store_type|
|
6
|
+
%w{current other}.each do |mode|
|
7
|
+
%w{AnyInstance#new AnyInstance::Inner#new}.each do |descriptor|
|
8
|
+
|
9
|
+
describe '>> %s process using :%s store (%s instance)' % [mode, store_type, descriptor] do
|
10
|
+
|
11
|
+
before do
|
12
|
+
@descriptor = descriptor
|
13
|
+
@klass = klassify(descriptor)
|
14
|
+
@instance = @klass.new
|
15
|
+
@store_type = store_type
|
16
|
+
end
|
17
|
+
|
18
|
+
behaves_like "has #{mode} process setup"
|
19
|
+
|
20
|
+
should "clear hash generated stub and return original value" do
|
21
|
+
original_value = @instance.say
|
22
|
+
@klass.xstub({:say => 'HELLO'}, :instance => true)
|
23
|
+
CrossStub.clear
|
24
|
+
@call["#{@descriptor}.say"].should.equal original_value
|
25
|
+
end
|
26
|
+
|
27
|
+
should "clear hash generated stub and raise NoMethodError" do
|
28
|
+
should.raise(NoMethodError) do
|
29
|
+
@klass.xstub({:blurb => 'blah blah'}, :instance => true)
|
30
|
+
CrossStub.clear
|
31
|
+
@call["#{@descriptor}.blurb"]
|
32
|
+
end
|
33
|
+
end
|
34
|
+
|
35
|
+
should "clear symbol generated stub and return original value" do
|
36
|
+
original_value = @instance.say
|
37
|
+
@klass.xstub(:say, :instance => true)
|
38
|
+
CrossStub.clear
|
39
|
+
@call["#{@descriptor}.say"].should.equal original_value
|
40
|
+
end
|
41
|
+
|
42
|
+
should "clear symbol generated stub and raise NoMethodError" do
|
43
|
+
should.raise(NoMethodError) do
|
44
|
+
@klass.xstub(:blurb, :instance => true)
|
45
|
+
CrossStub.clear
|
46
|
+
@call["#{@descriptor}.blurb"]
|
47
|
+
end
|
48
|
+
end
|
49
|
+
|
50
|
+
should "clear block generated stub and return original value" do
|
51
|
+
original_value = @instance.say
|
52
|
+
@klass.xstub(:instance => true) do
|
53
|
+
def say ; 'HELLO' ; end
|
54
|
+
end
|
55
|
+
CrossStub.clear
|
56
|
+
@call["#{@descriptor}.say"].should.equal original_value
|
57
|
+
end
|
58
|
+
|
59
|
+
should "clear block generated stub and raise NoMethodError" do
|
60
|
+
should.raise(NoMethodError) do
|
61
|
+
@klass.xstub(:instance => true) do
|
62
|
+
def blurb ; 'blah blah' ; end
|
63
|
+
end
|
64
|
+
CrossStub.clear
|
65
|
+
@call["#{@descriptor}.blurb"]
|
66
|
+
end
|
67
|
+
end
|
68
|
+
|
69
|
+
should "always clear previously generated stub" do
|
70
|
+
original_value = @instance.say
|
71
|
+
|
72
|
+
# Stub an existing method
|
73
|
+
@klass.xstub({:say => 'HELLO'}, :instance => true)
|
74
|
+
@call["#{@descriptor}.say"]
|
75
|
+
|
76
|
+
# Clear stubs without refreshing another process
|
77
|
+
CrossStub.clear
|
78
|
+
CrossStub.setup(cache_store(@store_type))
|
79
|
+
|
80
|
+
# Stub a non-existing method
|
81
|
+
@klass.xstub({:blurb => 'blah blah'}, :instance => true)
|
82
|
+
@call["#{@descriptor}.blurb"]
|
83
|
+
|
84
|
+
# Make sure existing method returns to original method
|
85
|
+
@call["#{@descriptor}.say"].should.equal original_value
|
86
|
+
end
|
87
|
+
|
88
|
+
should "always clear previously generated stub and raise NoMethodError" do
|
89
|
+
# Stub a non-existing method
|
90
|
+
@klass.xstub({:blurb => 'blah blah'}, :instance => true)
|
91
|
+
@call["#{@descriptor}.blurb"]
|
92
|
+
|
93
|
+
# Clear stubs without refreshing another process
|
94
|
+
CrossStub.clear
|
95
|
+
CrossStub.setup(cache_store(@store_type))
|
96
|
+
|
97
|
+
# Stub an existing method
|
98
|
+
@klass.xstub({:say => 'HELLO'}, :instance => true)
|
99
|
+
@call["#{@descriptor}.say"]
|
100
|
+
|
101
|
+
# Make sure accessing non-existing method throws error
|
102
|
+
should.raise(NoMethodError) { @call["#{@descriptor}.blurb"] }
|
103
|
+
end
|
104
|
+
|
105
|
+
should "clear for method not implemented in ruby and return original value" do
|
106
|
+
Time.xstub(:day => 99, :instance => true)
|
107
|
+
CrossStub.clear
|
108
|
+
value = nil
|
109
|
+
should.not.raise(NoMethodError) { value = @call['Time#new.day'] }
|
110
|
+
value.should.not.equal 99
|
111
|
+
end
|
112
|
+
|
113
|
+
end
|
114
|
+
|
115
|
+
end
|
116
|
+
end
|
117
|
+
end
|
118
|
+
|
119
|
+
end
|
@@ -0,0 +1,118 @@
|
|
1
|
+
require File.join(File.dirname(__FILE__), 'shared_spec')
|
2
|
+
|
3
|
+
describe 'Clearing Stubs' do
|
4
|
+
|
5
|
+
each_cache_store do |store_type|
|
6
|
+
%w{current other}.each do |mode|
|
7
|
+
%w{AnyClass AnyClass::Inner AnyModule AnyModule::Inner}.each do |descriptor|
|
8
|
+
|
9
|
+
describe '>> %s process using :%s store (%s)' % [mode, store_type, descriptor] do
|
10
|
+
|
11
|
+
before do
|
12
|
+
@descriptor = descriptor
|
13
|
+
@klass = klassify(descriptor)
|
14
|
+
@store_type = store_type
|
15
|
+
end
|
16
|
+
|
17
|
+
behaves_like "has #{mode} process setup"
|
18
|
+
|
19
|
+
should "clear hash generated stub and return original value" do
|
20
|
+
original_value = @klass.say
|
21
|
+
@klass.xstub(:say => 'HELLO')
|
22
|
+
CrossStub.clear
|
23
|
+
@call["#{@descriptor}.say"].should.equal original_value
|
24
|
+
end
|
25
|
+
|
26
|
+
should "clear hash generated stub and raise NoMethodError" do
|
27
|
+
should.raise(NoMethodError) do
|
28
|
+
@klass.xstub(:bang => 'OOPS')
|
29
|
+
CrossStub.clear
|
30
|
+
@call["#{@descriptor}.bang"]
|
31
|
+
end
|
32
|
+
end
|
33
|
+
|
34
|
+
should "clear symbol generated stub and return original value" do
|
35
|
+
original_value = @klass.say
|
36
|
+
@klass.xstub(:say)
|
37
|
+
CrossStub.clear
|
38
|
+
@call["#{@descriptor}.say"].should.equal original_value
|
39
|
+
end
|
40
|
+
|
41
|
+
should "clear symbol generated stub and raise NoMethodError" do
|
42
|
+
should.raise(NoMethodError) do
|
43
|
+
@klass.xstub(:bang)
|
44
|
+
CrossStub.clear
|
45
|
+
@call["#{@descriptor}.bang"]
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
should "clear block generated stub and return original value" do
|
50
|
+
original_value = @klass.say
|
51
|
+
@klass.xstub do
|
52
|
+
def say ; 'HELLO' ; end
|
53
|
+
end
|
54
|
+
CrossStub.clear
|
55
|
+
@call["#{@descriptor}.say"].should.equal original_value
|
56
|
+
end
|
57
|
+
|
58
|
+
should "clear block generated stub and raise NoMethodError" do
|
59
|
+
should.raise(NoMethodError) do
|
60
|
+
@klass.xstub do
|
61
|
+
def bang ; 'OOPS' ; end
|
62
|
+
end
|
63
|
+
CrossStub.clear
|
64
|
+
@call["#{@descriptor}.bang"]
|
65
|
+
end
|
66
|
+
end
|
67
|
+
|
68
|
+
should "always clear previously generated stub" do
|
69
|
+
original_value = @klass.say
|
70
|
+
|
71
|
+
# Stub an existing method
|
72
|
+
@klass.xstub(:say => 'HELLO')
|
73
|
+
@call["#{@descriptor}.say"]
|
74
|
+
|
75
|
+
# Clear stubs without refreshing another process
|
76
|
+
CrossStub.clear
|
77
|
+
CrossStub.setup(cache_store(@store_type))
|
78
|
+
|
79
|
+
# Stub a non-existing method
|
80
|
+
@klass.xstub(:bang => 'OOPS')
|
81
|
+
@call["#{@descriptor}.bang"]
|
82
|
+
|
83
|
+
# Make sure existing method returns to original method
|
84
|
+
@call["#{@descriptor}.say"].should.equal original_value
|
85
|
+
end
|
86
|
+
|
87
|
+
should "always clear previously generated stub and raise NoMethodError" do
|
88
|
+
# Stub a non-existing method
|
89
|
+
@klass.xstub(:bang => 'OOPS')
|
90
|
+
@call["#{@descriptor}.bang"]
|
91
|
+
|
92
|
+
# Clear stubs without refreshing another process
|
93
|
+
CrossStub.clear
|
94
|
+
CrossStub.setup(cache_store(@store_type))
|
95
|
+
|
96
|
+
# Stub an existing method
|
97
|
+
@klass.xstub(:say => 'HELLO')
|
98
|
+
@call["#{@descriptor}.say"]
|
99
|
+
|
100
|
+
# Make sure accessing non-existing method throws error
|
101
|
+
should.raise(NoMethodError) { @call["#{@descriptor}.bang"] }
|
102
|
+
end
|
103
|
+
|
104
|
+
should "clear for method not implemented in ruby and return original value" do
|
105
|
+
Time.xstub(:now => 'abc')
|
106
|
+
CrossStub.clear
|
107
|
+
value = nil
|
108
|
+
should.not.raise(NoMethodError) { value = @call['Time.now'] }
|
109
|
+
value.should.not.equal 'abc'
|
110
|
+
end
|
111
|
+
|
112
|
+
end
|
113
|
+
|
114
|
+
end
|
115
|
+
end
|
116
|
+
end
|
117
|
+
|
118
|
+
end
|
@@ -0,0 +1,91 @@
|
|
1
|
+
require File.join(File.dirname(__FILE__), 'shared_spec')
|
2
|
+
|
3
|
+
describe 'Creating Instance Stubs' do
|
4
|
+
|
5
|
+
each_cache_store do |store_type|
|
6
|
+
%w{current other}.each do |mode|
|
7
|
+
%w{AnyInstance#new AnyInstance::Inner#new}.each do |descriptor|
|
8
|
+
|
9
|
+
describe '>> %s process using :%s store (%s)' % [mode, store_type, descriptor] do
|
10
|
+
|
11
|
+
before do
|
12
|
+
@descriptor = descriptor
|
13
|
+
@klass = klassify(descriptor)
|
14
|
+
@store_type = store_type
|
15
|
+
end
|
16
|
+
|
17
|
+
behaves_like "has #{mode} process setup"
|
18
|
+
|
19
|
+
should "create with hash argument(s)" do
|
20
|
+
@klass.xstub({:bang => 'OOPS', :say => 'HELLO'}, :instance => true)
|
21
|
+
@call["#{@descriptor}.bang"].should.equal 'OOPS'
|
22
|
+
@call["#{@descriptor}.say"].should.equal 'HELLO'
|
23
|
+
end
|
24
|
+
|
25
|
+
should "create with symbol argument(s)" do
|
26
|
+
@klass.xstub(:bang, :instance => true)
|
27
|
+
@call["#{@descriptor}.bang"].should.equal nil
|
28
|
+
end
|
29
|
+
|
30
|
+
should "create with block with no argument" do
|
31
|
+
@klass.xstub(:instance => true) do
|
32
|
+
def bang ; 'OOPS' ; end
|
33
|
+
end
|
34
|
+
@call["#{@descriptor}.bang"].should.equal 'OOPS'
|
35
|
+
end
|
36
|
+
|
37
|
+
should "create with symbol & block with no argument" do
|
38
|
+
@klass.xstub(:bang, :instance => true) do
|
39
|
+
def say ; 'HELLO' ; end
|
40
|
+
end
|
41
|
+
@call["#{@descriptor}.bang"].should.equal nil
|
42
|
+
@call["#{@descriptor}.say"].should.equal 'HELLO'
|
43
|
+
end
|
44
|
+
|
45
|
+
should "create with hash & block with no argument" do
|
46
|
+
@klass.xstub({:bang => 'OOPS'}, :instance => true) do
|
47
|
+
def say ; 'HELLO' ; end
|
48
|
+
end
|
49
|
+
@call["#{@descriptor}.bang"].should.equal 'OOPS'
|
50
|
+
@call["#{@descriptor}.say"].should.equal 'HELLO'
|
51
|
+
end
|
52
|
+
|
53
|
+
should "always create the most recent" do
|
54
|
+
found, expected = [], ['OOPS', 'OOOPS', 'OOOOPS']
|
55
|
+
stub_and_get_value = lambda do |value|
|
56
|
+
@klass.xstub({:bang => value}, :instance => true)
|
57
|
+
@call["#{@descriptor}.bang"]
|
58
|
+
end
|
59
|
+
|
60
|
+
found << stub_and_get_value[expected[0]]
|
61
|
+
found << stub_and_get_value[expected[1]]
|
62
|
+
|
63
|
+
CrossStub.clear
|
64
|
+
CrossStub.setup(cache_store(@store_type))
|
65
|
+
|
66
|
+
found << stub_and_get_value[expected[2]]
|
67
|
+
found.should.equal expected
|
68
|
+
end
|
69
|
+
|
70
|
+
should "create stub with dependency on other stub" do
|
71
|
+
@klass.xstub({:something => 'HELLO'}, :instance => true) do
|
72
|
+
def do_action(who, action)
|
73
|
+
%\#{who} #{action} #{something}\
|
74
|
+
end
|
75
|
+
end
|
76
|
+
@call["#{@descriptor}.do_action.i.say"].should.equal 'i say HELLO'
|
77
|
+
end
|
78
|
+
|
79
|
+
should "create for method not implemented in ruby" do
|
80
|
+
day = 99
|
81
|
+
Time.xstub({:day => day}, :instance => true)
|
82
|
+
@call['Time#new.day'].should.equal day
|
83
|
+
end
|
84
|
+
|
85
|
+
end
|
86
|
+
|
87
|
+
end
|
88
|
+
end
|
89
|
+
end
|
90
|
+
|
91
|
+
end
|
@@ -0,0 +1,95 @@
|
|
1
|
+
require File.join(File.dirname(__FILE__), 'shared_spec')
|
2
|
+
|
3
|
+
describe 'Creating Stubs' do
|
4
|
+
|
5
|
+
each_cache_store do |store_type|
|
6
|
+
%w{current other}.each do |mode|
|
7
|
+
%w{AnyClass AnyModule AnyClass::Inner AnyModule::Inner}.each do |descriptor|
|
8
|
+
|
9
|
+
describe '>> %s process using :%s store (%s)' % [mode, store_type, descriptor] do
|
10
|
+
|
11
|
+
before do
|
12
|
+
@descriptor = descriptor
|
13
|
+
@klass = klassify(descriptor)
|
14
|
+
@store_type = store_type
|
15
|
+
end
|
16
|
+
|
17
|
+
behaves_like "has #{mode} process setup"
|
18
|
+
|
19
|
+
should "create with hash argument(s)" do
|
20
|
+
@klass.xstub(:bang => 'OOPS', :say => 'HELLO')
|
21
|
+
@call["#{@descriptor}.bang"].should.equal 'OOPS'
|
22
|
+
@call["#{@descriptor}.say"].should.equal 'HELLO'
|
23
|
+
end
|
24
|
+
|
25
|
+
should "create with symbol argument(s)" do
|
26
|
+
@klass.xstub(:bang)
|
27
|
+
@call["#{@descriptor}.bang"].should.equal nil
|
28
|
+
end
|
29
|
+
|
30
|
+
should "create with block with no argument" do
|
31
|
+
@klass.xstub do
|
32
|
+
def bang ; 'OOPS' ; end
|
33
|
+
end
|
34
|
+
@call["#{@descriptor}.bang"].should.equal 'OOPS'
|
35
|
+
end
|
36
|
+
|
37
|
+
should "create with symbol & block with no argument" do
|
38
|
+
@klass.xstub(:bang) do
|
39
|
+
def say
|
40
|
+
'HELLO'
|
41
|
+
end
|
42
|
+
end
|
43
|
+
@call["#{@descriptor}.bang"].should.equal nil
|
44
|
+
@call["#{@descriptor}.say"].should.equal 'HELLO'
|
45
|
+
end
|
46
|
+
|
47
|
+
should "create with hash & block with no argument" do
|
48
|
+
@klass.xstub(:bang => 'OOPS') do
|
49
|
+
def say
|
50
|
+
'HELLO'
|
51
|
+
end
|
52
|
+
end
|
53
|
+
@call["#{@descriptor}.bang"].should.equal 'OOPS'
|
54
|
+
@call["#{@descriptor}.say"].should.equal 'HELLO'
|
55
|
+
end
|
56
|
+
|
57
|
+
should "always create the most recent" do
|
58
|
+
found, expected = [], ['OOPS', 'OOOPS', 'OOOOPS']
|
59
|
+
stub_and_get_value = lambda do |value|
|
60
|
+
@klass.xstub(:bang => value)
|
61
|
+
@call["#{@descriptor}.bang"]
|
62
|
+
end
|
63
|
+
|
64
|
+
found << stub_and_get_value[expected[0]]
|
65
|
+
found << stub_and_get_value[expected[1]]
|
66
|
+
|
67
|
+
CrossStub.clear
|
68
|
+
CrossStub.setup(cache_store(@store_type))
|
69
|
+
|
70
|
+
found << stub_and_get_value[expected[2]]
|
71
|
+
found.should.equal expected
|
72
|
+
end
|
73
|
+
|
74
|
+
should "create stub with dependency on other stub" do
|
75
|
+
@klass.xstub(:something => 'HELLO') do
|
76
|
+
def do_action(who, action)
|
77
|
+
%\#{who} #{action} #{something}\
|
78
|
+
end
|
79
|
+
end
|
80
|
+
@call["#{@descriptor}.do_action.i.say"].should.equal 'i say HELLO'
|
81
|
+
end
|
82
|
+
|
83
|
+
should "create for method not implemented in ruby" do
|
84
|
+
now = Time.now - 365*60*60*24
|
85
|
+
Time.xstub(:now => now)
|
86
|
+
@call['Time.now'].should.equal now
|
87
|
+
end
|
88
|
+
|
89
|
+
end
|
90
|
+
|
91
|
+
end
|
92
|
+
end
|
93
|
+
end
|
94
|
+
|
95
|
+
end
|