casting 1.0.1 → 1.0.2
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +41 -0
- data/Rakefile +4 -4
- data/lib/casting/client.rb +12 -13
- data/lib/casting/context.rb +9 -15
- data/lib/casting/delegation.rb +33 -35
- data/lib/casting/enum.rb +3 -1
- data/lib/casting/method_consolidator.rb +5 -5
- data/lib/casting/missing_method_client.rb +16 -17
- data/lib/casting/missing_method_client_class.rb +3 -4
- data/lib/casting/null.rb +8 -2
- data/lib/casting/super_delegate.rb +11 -12
- data/lib/casting/version.rb +1 -1
- data/lib/casting.rb +6 -8
- metadata +3 -29
- data/test/casting_enum_test.rb +0 -40
- data/test/casting_test.rb +0 -89
- data/test/class_refinement_test.rb +0 -119
- data/test/client_test.rb +0 -81
- data/test/context_test.rb +0 -80
- data/test/delegation_test.rb +0 -198
- data/test/frozen_client_test.rb +0 -14
- data/test/method_consolidator_test.rb +0 -81
- data/test/missing_method_client_test.rb +0 -203
- data/test/module_cleanup_test.rb +0 -43
- data/test/null_module_test.rb +0 -43
- data/test/super_test.rb +0 -80
- data/test/test_helper.rb +0 -97
@@ -1,203 +0,0 @@
|
|
1
|
-
require 'test_helper'
|
2
|
-
|
3
|
-
module One
|
4
|
-
def similar
|
5
|
-
"from One"
|
6
|
-
end
|
7
|
-
end
|
8
|
-
|
9
|
-
module Two
|
10
|
-
def similar
|
11
|
-
"from Two"
|
12
|
-
end
|
13
|
-
end
|
14
|
-
|
15
|
-
describe Casting::MissingMethodClient, '#cast_as' do
|
16
|
-
let(:client){
|
17
|
-
test_person.extend(Casting::Client, Casting::MissingMethodClient)
|
18
|
-
}
|
19
|
-
|
20
|
-
it "sets the object's delegate for missing methods" do
|
21
|
-
client.cast_as(TestPerson::Greeter)
|
22
|
-
assert_equal 'hello', client.greet
|
23
|
-
end
|
24
|
-
|
25
|
-
it "delegates to objects of the same type" do
|
26
|
-
# avoid using another client
|
27
|
-
client = test_person
|
28
|
-
client.extend(TestPerson::Greeter)
|
29
|
-
attendant = client.clone
|
30
|
-
client.extend(Casting::Client, Casting::MissingMethodClient)
|
31
|
-
|
32
|
-
client.singleton_class.send(:undef_method, :greet)
|
33
|
-
client.cast_as(attendant)
|
34
|
-
assert_equal 'hello', client.greet
|
35
|
-
end
|
36
|
-
|
37
|
-
it "raises an error when given the client object" do
|
38
|
-
assert_raises(Casting::InvalidAttendant){
|
39
|
-
client.cast_as(client)
|
40
|
-
}
|
41
|
-
end
|
42
|
-
|
43
|
-
it "returns the object for further operation" do
|
44
|
-
jim = test_person.extend(Casting::Client, Casting::MissingMethodClient)
|
45
|
-
|
46
|
-
assert_equal 'hello', jim.cast_as(TestPerson::Greeter).greet
|
47
|
-
end
|
48
|
-
|
49
|
-
it "delegates methods to the last module added containing the method" do
|
50
|
-
jim = test_person.extend(Casting::Client, Casting::MissingMethodClient)
|
51
|
-
|
52
|
-
assert_equal "from Two", jim.cast_as(One, Two).similar
|
53
|
-
end
|
54
|
-
end
|
55
|
-
|
56
|
-
describe Casting::MissingMethodClient, '#uncast' do
|
57
|
-
let(:client){
|
58
|
-
test_person.extend(Casting::Client, Casting::MissingMethodClient)
|
59
|
-
}
|
60
|
-
|
61
|
-
it "removes the last added delegate" do
|
62
|
-
client.cast_as(TestPerson::Greeter)
|
63
|
-
assert_equal 'hello', client.greet
|
64
|
-
client.uncast
|
65
|
-
assert_raises(NoMethodError){ client.greet }
|
66
|
-
end
|
67
|
-
|
68
|
-
it "maintains any previously added delegates" do
|
69
|
-
client.cast_as(TestPerson::Verbose)
|
70
|
-
assert_equal 'one,two', client.verbose('one', 'two')
|
71
|
-
client.uncast
|
72
|
-
assert_raises(NoMethodError){ client.verbose('one', 'two') }
|
73
|
-
end
|
74
|
-
|
75
|
-
it "returns the object for further operation" do
|
76
|
-
jim = test_person.extend(Casting::Client, Casting::MissingMethodClient)
|
77
|
-
|
78
|
-
assert_equal 'name from TestPerson', jim.uncast.name
|
79
|
-
end
|
80
|
-
|
81
|
-
it "removes the specified number of delegates" do
|
82
|
-
jim = test_person.extend(Casting::Client, Casting::MissingMethodClient)
|
83
|
-
jim.cast_as(TestPerson::Greeter, TestPerson::Verbose)
|
84
|
-
|
85
|
-
assert_includes(jim.delegated_methods(true), :psst)
|
86
|
-
assert_includes(jim.delegated_methods(true), :verbose)
|
87
|
-
|
88
|
-
jim.uncast(2)
|
89
|
-
|
90
|
-
refute_includes(jim.delegated_methods(true), :psst)
|
91
|
-
refute_includes(jim.delegated_methods(true), :verbose)
|
92
|
-
end
|
93
|
-
end
|
94
|
-
|
95
|
-
describe Casting::MissingMethodClient, '#delegated_methods' do
|
96
|
-
let(:client){
|
97
|
-
object = test_person.extend(Casting::Client, Casting::MissingMethodClient)
|
98
|
-
object.cast_as(TestPerson::Greeter)
|
99
|
-
object
|
100
|
-
}
|
101
|
-
|
102
|
-
it "returns all instance methods including private from the object's delegates" do
|
103
|
-
assert_includes(client.delegated_methods(true), :psst)
|
104
|
-
end
|
105
|
-
|
106
|
-
it "returns all public instance methods from the object and it's delegates" do
|
107
|
-
refute_includes(client.delegated_methods(false), :psst)
|
108
|
-
end
|
109
|
-
|
110
|
-
it "returns all protected instance methods from the object and it's delegates" do
|
111
|
-
assert_includes(client.delegated_methods(true), :hey)
|
112
|
-
end
|
113
|
-
end
|
114
|
-
|
115
|
-
describe Casting::MissingMethodClient, '#delegated_public_methods' do
|
116
|
-
let(:client){
|
117
|
-
object = test_person.extend(Casting::Client, Casting::MissingMethodClient)
|
118
|
-
object.cast_as(TestPerson::Greeter)
|
119
|
-
object
|
120
|
-
}
|
121
|
-
|
122
|
-
it "returns all public methods from the object's delegates" do
|
123
|
-
assert_includes(client.delegated_public_methods, :greet)
|
124
|
-
end
|
125
|
-
|
126
|
-
it "excludes all private methods from the object's delegates" do
|
127
|
-
refute_includes(client.delegated_public_methods, :psst)
|
128
|
-
end
|
129
|
-
|
130
|
-
it "excludes all protected methods from the object's delegates" do
|
131
|
-
refute_includes(client.delegated_public_methods, :hey)
|
132
|
-
end
|
133
|
-
|
134
|
-
it "includes methods from superclasses" do
|
135
|
-
client.cast_as(Nested)
|
136
|
-
assert_includes(client.delegated_public_methods(true), :nested_deep)
|
137
|
-
end
|
138
|
-
|
139
|
-
it "excludes methods from superclasses" do
|
140
|
-
client.cast_as(Nested)
|
141
|
-
refute_includes(client.delegated_public_methods(false), :nested_deep)
|
142
|
-
end
|
143
|
-
end
|
144
|
-
|
145
|
-
describe Casting::MissingMethodClient, '#delegated_protected_methods' do
|
146
|
-
let(:client){
|
147
|
-
object = test_person.extend(Casting::Client, Casting::MissingMethodClient)
|
148
|
-
object.cast_as(TestPerson::Greeter)
|
149
|
-
object
|
150
|
-
}
|
151
|
-
|
152
|
-
it "excludes all public methods from the object's delegates" do
|
153
|
-
refute_includes(client.delegated_protected_methods, :greet)
|
154
|
-
end
|
155
|
-
|
156
|
-
it "excludes all private methods from the object's delegates" do
|
157
|
-
refute_includes(client.delegated_protected_methods, :psst)
|
158
|
-
end
|
159
|
-
|
160
|
-
it "includes all protected methods from the object's delegates" do
|
161
|
-
assert_includes(client.delegated_protected_methods, :hey)
|
162
|
-
end
|
163
|
-
|
164
|
-
it "includes methods from superclasses" do
|
165
|
-
client.cast_as(Nested)
|
166
|
-
assert_includes(client.delegated_protected_methods(true), :protected_nested_deep)
|
167
|
-
end
|
168
|
-
|
169
|
-
it "excludes methods from superclasses" do
|
170
|
-
client.cast_as(Nested)
|
171
|
-
refute_includes(client.delegated_protected_methods(false), :protected_nested_deep)
|
172
|
-
end
|
173
|
-
end
|
174
|
-
|
175
|
-
describe Casting::MissingMethodClient, '#delegated_private_methods' do
|
176
|
-
let(:client){
|
177
|
-
object = test_person.extend(Casting::Client, Casting::MissingMethodClient)
|
178
|
-
object.cast_as(TestPerson::Greeter)
|
179
|
-
object
|
180
|
-
}
|
181
|
-
|
182
|
-
it "excludes all public methods from the object's delegates" do
|
183
|
-
refute_includes(client.delegated_private_methods, :greet)
|
184
|
-
end
|
185
|
-
|
186
|
-
it "includes all private methods from the object's delegates" do
|
187
|
-
assert_includes(client.delegated_private_methods, :psst)
|
188
|
-
end
|
189
|
-
|
190
|
-
it "excludes all protected methods from the object's delegates" do
|
191
|
-
refute_includes(client.delegated_private_methods, :hey)
|
192
|
-
end
|
193
|
-
|
194
|
-
it "includes methods from superclasses" do
|
195
|
-
client.cast_as(Nested)
|
196
|
-
assert_includes(client.delegated_private_methods(true), :private_nested_deep)
|
197
|
-
end
|
198
|
-
|
199
|
-
it "excludes methods from superclasses" do
|
200
|
-
client.cast_as(Nested)
|
201
|
-
refute_includes(client.delegated_private_methods(false), :private_nested_deep)
|
202
|
-
end
|
203
|
-
end
|
data/test/module_cleanup_test.rb
DELETED
@@ -1,43 +0,0 @@
|
|
1
|
-
require 'test_helper'
|
2
|
-
|
3
|
-
module Cleaner
|
4
|
-
def self.uncast_object(object)
|
5
|
-
object.send(:remove_instance_variable, :@cleaner_message)
|
6
|
-
end
|
7
|
-
|
8
|
-
def self.cast_object(object)
|
9
|
-
object.instance_variable_set(:@cleaner_message, "#{object.name} will be cleaned up")
|
10
|
-
end
|
11
|
-
|
12
|
-
def cleaner_message
|
13
|
-
@cleaner_message
|
14
|
-
end
|
15
|
-
end
|
16
|
-
|
17
|
-
class CleanupPerson
|
18
|
-
include Casting::Client
|
19
|
-
delegate_missing_methods
|
20
|
-
attr_accessor :name
|
21
|
-
end
|
22
|
-
|
23
|
-
describe 'modules with setup tasks' do
|
24
|
-
it 'allows modules to setup an object when cast_as' do
|
25
|
-
jim = CleanupPerson.new
|
26
|
-
jim.name = 'Jim'
|
27
|
-
jim.cast_as(Cleaner)
|
28
|
-
assert_equal "Jim will be cleaned up", jim.cleaner_message
|
29
|
-
assert_equal "Jim will be cleaned up", jim.instance_variable_get(:@cleaner_message)
|
30
|
-
end
|
31
|
-
end
|
32
|
-
|
33
|
-
describe 'modules with cleanup tasks' do
|
34
|
-
it 'allows modules to cleanup their required attributes when uncast' do
|
35
|
-
jim = CleanupPerson.new
|
36
|
-
jim.name = 'Jim'
|
37
|
-
jim.cast_as(Cleaner)
|
38
|
-
assert_equal "Jim will be cleaned up", jim.cleaner_message
|
39
|
-
assert_equal "Jim will be cleaned up", jim.instance_variable_get(:@cleaner_message)
|
40
|
-
jim.uncast
|
41
|
-
refute jim.instance_variable_defined?(:@cleaner_message)
|
42
|
-
end
|
43
|
-
end
|
data/test/null_module_test.rb
DELETED
@@ -1,43 +0,0 @@
|
|
1
|
-
require 'test_helper'
|
2
|
-
|
3
|
-
describe Casting::Null do
|
4
|
-
it 'will answer to any method with nil' do
|
5
|
-
client = TestPerson.new
|
6
|
-
client.extend(Casting::Client)
|
7
|
-
attendant = Casting::Null
|
8
|
-
|
9
|
-
assert_nil client.delegate('greet', attendant)
|
10
|
-
end
|
11
|
-
end
|
12
|
-
|
13
|
-
describe Casting::Blank do
|
14
|
-
it 'will answer to any method with an empty string' do
|
15
|
-
client = TestPerson.new
|
16
|
-
client.extend(Casting::Client)
|
17
|
-
attendant = Casting::Blank
|
18
|
-
|
19
|
-
assert_empty client.delegate('greet', attendant)
|
20
|
-
end
|
21
|
-
end
|
22
|
-
|
23
|
-
describe "making null objects" do
|
24
|
-
it "answers to missing methods" do
|
25
|
-
client = TestPerson.new
|
26
|
-
client.extend(Casting::Client)
|
27
|
-
client.delegate_missing_methods
|
28
|
-
attendant = Casting::Null
|
29
|
-
|
30
|
-
assert_respond_to client.cast_as(attendant), 'xyz'
|
31
|
-
end
|
32
|
-
end
|
33
|
-
|
34
|
-
describe "making blank objects" do
|
35
|
-
it "answers to missing methods" do
|
36
|
-
client = TestPerson.new
|
37
|
-
client.extend(Casting::Client)
|
38
|
-
client.delegate_missing_methods
|
39
|
-
attendant = Casting::Blank
|
40
|
-
|
41
|
-
assert_respond_to client.cast_as(attendant), 'xyz'
|
42
|
-
end
|
43
|
-
end
|
data/test/super_test.rb
DELETED
@@ -1,80 +0,0 @@
|
|
1
|
-
require 'test_helper'
|
2
|
-
|
3
|
-
module AnyWay
|
4
|
-
def which_way
|
5
|
-
"any way"
|
6
|
-
end
|
7
|
-
def way_with_args(one, two, &block)
|
8
|
-
[one, two, block&.call].compact.inspect
|
9
|
-
end
|
10
|
-
def way_with_keyword_args(one:, two:, &block)
|
11
|
-
[one, two, block&.call].compact.inspect
|
12
|
-
end
|
13
|
-
end
|
14
|
-
|
15
|
-
module ThisWay
|
16
|
-
include Casting::SuperDelegate
|
17
|
-
def which_way
|
18
|
-
"this way or #{super_delegate}"
|
19
|
-
end
|
20
|
-
def way_with_args(one, two, &block)
|
21
|
-
[one, two, block&.call].compact.inspect
|
22
|
-
end
|
23
|
-
def way_with_keyword_args(one:, two:, &block)
|
24
|
-
[one, two, block&.call].compact.inspect
|
25
|
-
end
|
26
|
-
def no_super
|
27
|
-
super_delegate
|
28
|
-
end
|
29
|
-
end
|
30
|
-
|
31
|
-
module ThatWay
|
32
|
-
include Casting::SuperDelegate
|
33
|
-
def which_way
|
34
|
-
"#{ super_delegate(ThatWay) } and that way!"
|
35
|
-
end
|
36
|
-
def way_with_args(one, two, &block)
|
37
|
-
super_delegate(one, two, block&.call).compact
|
38
|
-
end
|
39
|
-
def way_with_keyword_args(one:, two:, &block)
|
40
|
-
[one, two, block&.call].compact.inspect
|
41
|
-
end
|
42
|
-
end
|
43
|
-
|
44
|
-
describe Casting, 'modules using delegate_super' do
|
45
|
-
it 'call the method from the next delegate with the same arguments' do
|
46
|
-
client = TestPerson.new.extend(Casting::Client)
|
47
|
-
client.delegate_missing_methods
|
48
|
-
client.cast_as(AnyWay, ThatWay, ThisWay)
|
49
|
-
|
50
|
-
assert_equal 'this way or any way and that way!', client.which_way
|
51
|
-
end
|
52
|
-
|
53
|
-
it 'passes arguments' do
|
54
|
-
client = TestPerson.new.extend(Casting::Client)
|
55
|
-
client.delegate_missing_methods
|
56
|
-
client.cast_as(ThatWay, ThisWay)
|
57
|
-
|
58
|
-
assert_equal %{["first", "second", "block"]}, client.way_with_args('first', 'second'){ 'block' }
|
59
|
-
end
|
60
|
-
|
61
|
-
it 'passes keyword arguments' do
|
62
|
-
client = TestPerson.new.extend(Casting::Client)
|
63
|
-
client.delegate_missing_methods
|
64
|
-
client.cast_as(ThatWay, ThisWay)
|
65
|
-
|
66
|
-
assert_equal %{["first", "second", "block"]}, client.way_with_keyword_args(one: 'first', two: 'second'){ 'block' }
|
67
|
-
end
|
68
|
-
|
69
|
-
it 'raises an error when method is not defined' do
|
70
|
-
client = TestPerson.new.extend(Casting::Client)
|
71
|
-
client.delegate_missing_methods
|
72
|
-
client.cast_as(ThisWay)
|
73
|
-
|
74
|
-
err = expect{
|
75
|
-
client.no_super
|
76
|
-
}.must_raise(NoMethodError)
|
77
|
-
|
78
|
-
expect(err.message).must_match(/super_delegate: no delegate method \`no_super' for \#<TestPerson:\dx[a-z0-9]*> from ThisWay/)
|
79
|
-
end
|
80
|
-
end
|
data/test/test_helper.rb
DELETED
@@ -1,97 +0,0 @@
|
|
1
|
-
require "simplecov"
|
2
|
-
SimpleCov.start do
|
3
|
-
add_filter 'test'
|
4
|
-
end
|
5
|
-
require 'minitest/autorun'
|
6
|
-
require 'casting'
|
7
|
-
|
8
|
-
BlockTestPerson = Struct.new(:name)
|
9
|
-
BlockTestPerson.send(:include, Casting::Client)
|
10
|
-
BlockTestPerson.delegate_missing_methods
|
11
|
-
|
12
|
-
class TestPerson
|
13
|
-
def name
|
14
|
-
'name from TestPerson'
|
15
|
-
end
|
16
|
-
|
17
|
-
module Greeter
|
18
|
-
def greet
|
19
|
-
'hello'
|
20
|
-
end
|
21
|
-
|
22
|
-
protected
|
23
|
-
|
24
|
-
def hey; end
|
25
|
-
|
26
|
-
private
|
27
|
-
|
28
|
-
def psst; end
|
29
|
-
end
|
30
|
-
|
31
|
-
module Verbose
|
32
|
-
def verbose(arg1, arg2)
|
33
|
-
[arg1, arg2].join(',')
|
34
|
-
end
|
35
|
-
|
36
|
-
def verbose_keywords(key:, word:)
|
37
|
-
[key, word].join(',')
|
38
|
-
end
|
39
|
-
|
40
|
-
def verbose_multi_args(arg1, arg2, key:, word:, &block)
|
41
|
-
[arg1, arg2, key, word, block&.call].compact.join(',')
|
42
|
-
end
|
43
|
-
|
44
|
-
def verbose_flex(*args, **kwargs, &block)
|
45
|
-
[args, kwargs.map{|k,v| "#{k}:#{v}"}, block&.call].flatten.compact.join(',')
|
46
|
-
end
|
47
|
-
end
|
48
|
-
end
|
49
|
-
|
50
|
-
class TestGreeter
|
51
|
-
include TestPerson::Greeter
|
52
|
-
end
|
53
|
-
|
54
|
-
class SubTestPerson < TestPerson
|
55
|
-
def sub_method
|
56
|
-
'sub'
|
57
|
-
end
|
58
|
-
end
|
59
|
-
|
60
|
-
class Unrelated
|
61
|
-
module More
|
62
|
-
def unrelated
|
63
|
-
'unrelated'
|
64
|
-
end
|
65
|
-
end
|
66
|
-
include More
|
67
|
-
|
68
|
-
def class_defined
|
69
|
-
'oops!'
|
70
|
-
end
|
71
|
-
end
|
72
|
-
|
73
|
-
module Deep
|
74
|
-
def nested_deep; end
|
75
|
-
protected
|
76
|
-
def protected_nested_deep; end
|
77
|
-
private
|
78
|
-
def private_nested_deep; end
|
79
|
-
end
|
80
|
-
|
81
|
-
module Nested
|
82
|
-
include Deep
|
83
|
-
|
84
|
-
def nested; end
|
85
|
-
protected
|
86
|
-
def protected_nested; end
|
87
|
-
private
|
88
|
-
def private_nested; end
|
89
|
-
end
|
90
|
-
|
91
|
-
def test_person
|
92
|
-
TestPerson.new
|
93
|
-
end
|
94
|
-
|
95
|
-
def casting_person
|
96
|
-
test_person.extend(Casting::Client)
|
97
|
-
end
|