sinclair 1.9.0 → 1.11.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.
- checksums.yaml +4 -4
- data/.rubocop.yml +7 -1
- data/README.md +414 -324
- data/config/check_specs.yml +3 -4
- data/config/yardstick.yml +9 -1
- data/lib/sinclair/configurable.rb +2 -0
- data/lib/sinclair/equals_checker.rb +2 -0
- data/lib/sinclair/matchers/add_class_method.rb +26 -36
- data/lib/sinclair/matchers/add_instance_method.rb +59 -59
- data/lib/sinclair/matchers/add_method.rb +33 -35
- data/lib/sinclair/matchers/change_class_method.rb +22 -16
- data/lib/sinclair/matchers/change_instance_method.rb +46 -16
- data/lib/sinclair/matchers.rb +2 -8
- data/lib/sinclair/method_builder/base.rb +17 -2
- data/lib/sinclair/method_builder/call_method_builder.rb +49 -0
- data/lib/sinclair/method_builder.rb +5 -17
- data/lib/sinclair/method_definition/block_definition.rb +2 -0
- data/lib/sinclair/method_definition/call_definition.rb +49 -0
- data/lib/sinclair/method_definition/string_definition.rb +2 -2
- data/lib/sinclair/method_definition.rb +80 -26
- data/lib/sinclair/method_definitions.rb +25 -7
- data/lib/sinclair/options/builder.rb +8 -0
- data/lib/sinclair/options.rb +1 -13
- data/lib/sinclair/version.rb +1 -1
- data/lib/sinclair.rb +149 -62
- data/spec/integration/readme/sinclair/types_of_definition_spec.rb +47 -0
- data/spec/integration/yard/sinclair/add_class_method_spec.rb +51 -0
- data/spec/integration/yard/sinclair/add_method_spec.rb +60 -0
- data/spec/integration/yard/sinclair/eval_and_add_method_spec.rb +26 -0
- data/spec/integration/yard/sinclair/matchers/change_class_method_spec.rb +24 -0
- data/spec/integration/yard/sinclair/matchers/change_instance_method_spec.rb +40 -0
- data/spec/integration/yard/sinclair_spec.rb +0 -83
- data/spec/lib/sinclair/method_builder/base_spec.rb +15 -0
- data/spec/lib/sinclair/method_builder/call_method_builder_spec.rb +76 -0
- data/spec/lib/sinclair/method_builder_spec.rb +63 -20
- data/spec/lib/sinclair/method_definition/call_definition_spec.rb +33 -0
- data/spec/lib/sinclair/method_definition_spec.rb +129 -0
- data/spec/lib/sinclair/method_definitions_spec.rb +79 -1
- data/spec/lib/sinclair/options/builder_spec.rb +13 -0
- data/spec/lib/sinclair/options/class_methods_spec.rb +23 -8
- data/spec/lib/sinclair_spec.rb +6 -160
- data/spec/support/models/dummy_builder.rb +4 -1
- data/spec/support/models/dummy_class_builder.rb +3 -0
- data/spec/support/models/person.rb +1 -1
- data/spec/support/shared_examples/attribute_accessor.rb +103 -0
- data/spec/support/shared_examples/sinclair.rb +112 -0
- metadata +15 -2
data/config/check_specs.yml
CHANGED
@@ -1,10 +1,9 @@
|
|
1
1
|
ignore:
|
2
2
|
- lib/sinclair/comparable/class_methods.rb
|
3
|
+
- lib/sinclair/exception.rb
|
3
4
|
- lib/sinclair/matchers/add_method_to.rb
|
4
5
|
- lib/sinclair/matchers/add_method.rb
|
5
|
-
- lib/sinclair/version.rb
|
6
|
-
- lib/sinclair/method_builder/base.rb
|
7
|
-
- lib/sinclair/exception.rb
|
8
|
-
- lib/sinclair/matchers/method_to.rb
|
9
6
|
- lib/sinclair/matchers/base.rb
|
7
|
+
- lib/sinclair/matchers/method_to.rb
|
10
8
|
- lib/sinclair/matchers/change_method_on.rb
|
9
|
+
- lib/sinclair/version.rb
|
data/config/yardstick.yml
CHANGED
@@ -1,4 +1,4 @@
|
|
1
|
-
threshold:
|
1
|
+
threshold: 100
|
2
2
|
require_exact_threshold: false
|
3
3
|
rules:
|
4
4
|
ApiTag::Presence:
|
@@ -16,6 +16,8 @@ rules:
|
|
16
16
|
ExampleTag:
|
17
17
|
enabled: true
|
18
18
|
exclude:
|
19
|
+
- Sinclair#add_method
|
20
|
+
- Sinclair#add_class_method
|
19
21
|
- Sinclair::Configurable#config
|
20
22
|
- Sinclair::Configurable#reset_config
|
21
23
|
- Sinclair::Configurable#configure
|
@@ -23,6 +25,10 @@ rules:
|
|
23
25
|
- Sinclair::Options#==
|
24
26
|
- Sinclair::OptionsParser#options
|
25
27
|
- Sinclair::OptionsParser#options_object
|
28
|
+
- Sinclair::Matchers#add_method
|
29
|
+
- Sinclair::Matchers#add_class_method
|
30
|
+
- Sinclair::Matchers#change_method
|
31
|
+
- Sinclair::Matchers#change_class_method
|
26
32
|
ReturnTag:
|
27
33
|
enabled: true
|
28
34
|
exclude:
|
@@ -50,7 +56,9 @@ rules:
|
|
50
56
|
- Sinclair::Matchers::ChangeInstanceMethodOn#initialize
|
51
57
|
- Sinclair::MethodBuilder
|
52
58
|
- Sinclair::MethodBuilder::Base#initialize
|
59
|
+
- Sinclair::MethodBuilder::Accessor#initialize
|
53
60
|
- Sinclair::MethodDefinition#initialize
|
61
|
+
- Sinclair::MethodDefinition::CallDefinition#initialize
|
54
62
|
- Sinclair::MethodDefinition::BlockDefinition#initialize
|
55
63
|
- Sinclair::MethodDefinition::StringDefinition#initialize
|
56
64
|
- Sinclair::Options#initialize
|
@@ -81,6 +81,8 @@ class Sinclair
|
|
81
81
|
# @method as_options(options_hash = {})
|
82
82
|
# @api public
|
83
83
|
#
|
84
|
+
# Returns options with configurated values
|
85
|
+
#
|
84
86
|
# @param (see Sinclair::Config#as_options)
|
85
87
|
# @return (see Sinclair::Config#as_options)
|
86
88
|
# @example (see Sinclair::Config#as_options)
|
@@ -6,33 +6,32 @@ class Sinclair
|
|
6
6
|
# @author darthjee
|
7
7
|
#
|
8
8
|
# AddClassMethod is able to build an instance of {Sinclair::Matchers::AddClassMethodTo}
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
include AddMethod
|
9
|
+
class AddClassMethod < AddMethod
|
10
|
+
# @example Checking if a class had a class method added
|
11
|
+
# RSpec.configure do |config|
|
12
|
+
# config.include Sinclair::Matchers
|
13
|
+
# end
|
14
|
+
#
|
15
|
+
# class MyModel
|
16
|
+
# end
|
17
|
+
#
|
18
|
+
# RSpec.describe 'MyBuilder' do
|
19
|
+
# let(:clazz) { Class.new(MyModel) }
|
20
|
+
#
|
21
|
+
# let(:block) do
|
22
|
+
# proc do
|
23
|
+
# clazz.define_singleton_method(:new_method) { 2 }
|
24
|
+
# end
|
25
|
+
# end
|
26
|
+
#
|
27
|
+
# it do
|
28
|
+
# expect(&block).to add_class_method(:new_method).to(clazz)
|
29
|
+
# end
|
30
|
+
# end
|
31
|
+
#
|
32
|
+
# # outputs
|
33
|
+
# # should add method class_method 'new_method' to #<Class:0x000055b4d0a25c80>
|
34
|
+
with_final_matcher :to, AddClassMethodTo
|
36
35
|
|
37
36
|
private
|
38
37
|
|
@@ -45,15 +44,6 @@ class Sinclair
|
|
45
44
|
'You should specify which class the method is being added to' \
|
46
45
|
"add_class_method(:#{method_name}).to(klass)"
|
47
46
|
end
|
48
|
-
|
49
|
-
# @private
|
50
|
-
#
|
51
|
-
# Class of the real matcher
|
52
|
-
#
|
53
|
-
# @return [Class<Sinclair::Matchers::Base>]
|
54
|
-
def add_method_to_class
|
55
|
-
AddClassMethodTo
|
56
|
-
end
|
57
47
|
end
|
58
48
|
end
|
59
49
|
end
|
@@ -7,56 +7,65 @@ class Sinclair
|
|
7
7
|
#
|
8
8
|
# AddInstanceMethod is able to build an instance of {Sinclair::Matchers::AddInstanceMethodTo}
|
9
9
|
#
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
10
|
+
class AddInstanceMethod < AddMethod
|
11
|
+
# @example Using inside RSpec and checking an instance method being added
|
12
|
+
# RSpec.configure do |config|
|
13
|
+
# config.include Sinclair::Matchers
|
14
|
+
# end
|
15
|
+
#
|
16
|
+
# class MyModel
|
17
|
+
# end
|
18
|
+
#
|
19
|
+
# RSpec.describe "MyBuilder" do
|
20
|
+
# let(:clazz) { Class.new(MyModel) }
|
21
|
+
# let(:builder) { Sinclair.new(clazz) }
|
22
|
+
#
|
23
|
+
# before do
|
24
|
+
# builder.add_method(:new_method, "2")
|
25
|
+
# end
|
26
|
+
#
|
27
|
+
# it do
|
28
|
+
# expect { builder.build }.to add_method(:new_method).to(clazz)
|
29
|
+
# end
|
30
|
+
# end
|
31
|
+
#
|
32
|
+
# # Outputs
|
33
|
+
# # 'should add method 'new_method' to #<Class:0x000056441bf46608> instances'
|
34
|
+
#
|
35
|
+
# @example Using inside RSpec and checking instance
|
36
|
+
# RSpec.configure do |config|
|
37
|
+
# config.include Sinclair::Matchers
|
38
|
+
# end
|
39
|
+
#
|
40
|
+
# class MyModel
|
41
|
+
# end
|
42
|
+
#
|
43
|
+
# RSpec.describe "MyBuilder" do
|
44
|
+
# let(:clazz) { Class.new(MyModel) }
|
45
|
+
# let(:builder) { Sinclair.new(clazz) }
|
46
|
+
# let(:instance) { clazz.new }
|
47
|
+
#
|
48
|
+
# before do
|
49
|
+
# builder.add_method(:the_method, "true")
|
50
|
+
# end
|
51
|
+
#
|
52
|
+
# it do
|
53
|
+
# expect { builder.build }.to add_method(:the_method).to(instance)
|
54
|
+
# end
|
55
|
+
# end
|
56
|
+
#
|
57
|
+
# # Outputs
|
58
|
+
# # 'should add method 'the_method' to #<Class:0x000056441bf46608> instances'
|
59
|
+
with_final_matcher :to, AddInstanceMethodTo
|
60
|
+
|
61
|
+
# @method to(target = nil)
|
62
|
+
# @api public
|
63
|
+
#
|
64
|
+
# The matcher checks if an instance method was added to a class
|
65
|
+
#
|
66
|
+
# @param (see AddMethod#to)
|
67
|
+
#
|
68
|
+
# @return [AddClassMethodTo]
|
60
69
|
|
61
70
|
private
|
62
71
|
|
@@ -69,15 +78,6 @@ class Sinclair
|
|
69
78
|
'You should specify which instance the method is being added to' \
|
70
79
|
"add_method(:#{method_name}).to(instance)"
|
71
80
|
end
|
72
|
-
|
73
|
-
# @private
|
74
|
-
#
|
75
|
-
# Class of the real matcher
|
76
|
-
#
|
77
|
-
# @return [Class<Sinclair::Matchers::Base>]
|
78
|
-
def add_method_to_class
|
79
|
-
AddInstanceMethodTo
|
80
|
-
end
|
81
81
|
end
|
82
82
|
end
|
83
83
|
end
|
@@ -4,41 +4,39 @@ class Sinclair
|
|
4
4
|
module Matchers
|
5
5
|
# @api private
|
6
6
|
#
|
7
|
-
#
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
def to(target = nil)
|
41
|
-
add_method_to_class.new(target, method_name)
|
7
|
+
# Common methods for matchers
|
8
|
+
class AddMethod < Base
|
9
|
+
class << self
|
10
|
+
private
|
11
|
+
|
12
|
+
# @api private
|
13
|
+
# @private
|
14
|
+
#
|
15
|
+
# Add a method to generate the final matcher
|
16
|
+
#
|
17
|
+
# @param name [String,Symbol] the name of the method
|
18
|
+
# @param matcher_class [Class<AddMethodTo>] The matcher class to be returned
|
19
|
+
#
|
20
|
+
# @return (see Sinclair#build)
|
21
|
+
#
|
22
|
+
# @!macro with_final_matcher
|
23
|
+
# @!method $1(target = nil)
|
24
|
+
# @api public
|
25
|
+
#
|
26
|
+
# Builds final matcher
|
27
|
+
#
|
28
|
+
# The matcher checks if a method was added
|
29
|
+
# to a class or instance
|
30
|
+
#
|
31
|
+
# @param [Class,Object] target where the method will be added
|
32
|
+
#
|
33
|
+
# @return [$2]
|
34
|
+
def with_final_matcher(name, matcher_class)
|
35
|
+
matcher = matcher_class
|
36
|
+
Sinclair.new(self).tap do |builder|
|
37
|
+
builder.add_method(name) { |target| matcher.new(target, method_name) }
|
38
|
+
end.build
|
39
|
+
end
|
42
40
|
end
|
43
41
|
|
44
42
|
# @abstract
|
@@ -7,15 +7,30 @@ class Sinclair
|
|
7
7
|
#
|
8
8
|
# AddInstanceMethod is able to build an instance of
|
9
9
|
# {Sinclair::Matchers::ChangeClassMethodOn}
|
10
|
-
class ChangeClassMethod <
|
11
|
-
|
12
|
-
|
13
|
-
#
|
10
|
+
class ChangeClassMethod < AddMethod
|
11
|
+
# @example Checking if a class method has changed
|
12
|
+
# RSpec.configure do |config|
|
13
|
+
# config.include Sinclair::Matchers
|
14
|
+
# end
|
15
|
+
#
|
16
|
+
# class MyModel
|
17
|
+
# end
|
14
18
|
#
|
15
|
-
#
|
19
|
+
# RSpec.describe 'my test' do
|
20
|
+
# let(:builder) { Sinclair.new(klass) }
|
21
|
+
# let(:klass) { Class.new(MyModel) }
|
16
22
|
#
|
17
|
-
#
|
18
|
-
|
23
|
+
# before do
|
24
|
+
# builder.add_class_method(:the_method) { 10 }
|
25
|
+
# builder.build
|
26
|
+
# builder.add_class_method(:the_method) { 20 }
|
27
|
+
# end
|
28
|
+
#
|
29
|
+
# it do
|
30
|
+
# expect{ builder.build }.to change_class_method(:the_method).on(klass)
|
31
|
+
# end
|
32
|
+
# end
|
33
|
+
with_final_matcher :on, ChangeClassMethodOn
|
19
34
|
|
20
35
|
private
|
21
36
|
|
@@ -28,15 +43,6 @@ class Sinclair
|
|
28
43
|
'You should specify which class the method is being changed on' \
|
29
44
|
"change_class_method(:#{method_name}).on(klass)"
|
30
45
|
end
|
31
|
-
|
32
|
-
# @private
|
33
|
-
#
|
34
|
-
# Class of the real matcher
|
35
|
-
#
|
36
|
-
# @return [Class<ChangeClassMethodOn>]
|
37
|
-
def add_method_to_class
|
38
|
-
ChangeClassMethodOn
|
39
|
-
end
|
40
46
|
end
|
41
47
|
end
|
42
48
|
end
|
@@ -7,15 +7,54 @@ class Sinclair
|
|
7
7
|
#
|
8
8
|
# AddInstanceMethod is able to build an instance of
|
9
9
|
# {Sinclair::Matchers::ChangeInstanceMethodOn}
|
10
|
-
class ChangeInstanceMethod <
|
11
|
-
|
12
|
-
|
13
|
-
#
|
10
|
+
class ChangeInstanceMethod < AddMethod
|
11
|
+
# @example Checking if an instance method has changed
|
12
|
+
# RSpec.configure do |config|
|
13
|
+
# config.include Sinclair::Matchers
|
14
|
+
# end
|
15
|
+
#
|
16
|
+
# class MyModel
|
17
|
+
# end
|
18
|
+
#
|
19
|
+
# RSpec.describe 'my test' do
|
20
|
+
# let(:builder) { Sinclair.new(klass) }
|
21
|
+
# let(:klass) { Class.new(MyModel) }
|
22
|
+
#
|
23
|
+
# before do
|
24
|
+
# builder.add_method(:the_method) { 10 }
|
25
|
+
# builder.build
|
26
|
+
# builder.add_method(:the_method) { 20 }
|
27
|
+
# end
|
28
|
+
#
|
29
|
+
# it do
|
30
|
+
# expect{ builder.build }.to change_method(:the_method).on(klass)
|
31
|
+
# end
|
32
|
+
# end
|
33
|
+
#
|
34
|
+
# @example Checking if an instance method has changed on an instance
|
35
|
+
# RSpec.configure do |config|
|
36
|
+
# config.include Sinclair::Matchers
|
37
|
+
# end
|
38
|
+
#
|
39
|
+
# class MyModel
|
40
|
+
# end
|
14
41
|
#
|
15
|
-
#
|
42
|
+
# RSpec.describe 'my test' do
|
43
|
+
# let(:builder) { Sinclair.new(klass) }
|
44
|
+
# let(:instance) { klass.new }
|
45
|
+
# let(:klass) { Class.new(MyModel) }
|
16
46
|
#
|
17
|
-
#
|
18
|
-
|
47
|
+
# before do
|
48
|
+
# builder.add_method(:the_method) { 10 }
|
49
|
+
# builder.build
|
50
|
+
# builder.add_method(:the_method) { 20 }
|
51
|
+
# end
|
52
|
+
#
|
53
|
+
# it do
|
54
|
+
# expect{ builder.build }.to change_method(:the_method).on(instance)
|
55
|
+
# end
|
56
|
+
# end
|
57
|
+
with_final_matcher :on, ChangeInstanceMethodOn
|
19
58
|
|
20
59
|
private
|
21
60
|
|
@@ -28,15 +67,6 @@ class Sinclair
|
|
28
67
|
'You should specify which instance the method is being changed on' \
|
29
68
|
"change_method(:#{method_name}).on(instance)"
|
30
69
|
end
|
31
|
-
|
32
|
-
# @private
|
33
|
-
#
|
34
|
-
# Class of the real matcher
|
35
|
-
#
|
36
|
-
# @return [Class<Sinclair::Matchers::Base>]
|
37
|
-
def add_method_to_class
|
38
|
-
ChangeInstanceMethodOn
|
39
|
-
end
|
40
70
|
end
|
41
71
|
end
|
42
72
|
end
|
data/lib/sinclair/matchers.rb
CHANGED
@@ -6,8 +6,6 @@ class Sinclair
|
|
6
6
|
#
|
7
7
|
# Matchers module will have the DSL to be included in RSpec in order to have
|
8
8
|
# access to the matchers
|
9
|
-
#
|
10
|
-
# @example (see Sinclair::Matchers::AddMethod#to)
|
11
9
|
module Matchers
|
12
10
|
autoload :Base, 'sinclair/matchers/base'
|
13
11
|
autoload :AddInstanceMethod, 'sinclair/matchers/add_instance_method'
|
@@ -25,7 +23,6 @@ class Sinclair
|
|
25
23
|
|
26
24
|
# DSL to AddInstanceMethod
|
27
25
|
#
|
28
|
-
# @example (see Sinclair::Matchers)
|
29
26
|
# @example (see Sinclair::Matchers::AddInstanceMethod#to)
|
30
27
|
#
|
31
28
|
# @return [AddInstanceMethod] RSpec Matcher
|
@@ -35,7 +32,6 @@ class Sinclair
|
|
35
32
|
|
36
33
|
# DSL to AddClassMethod
|
37
34
|
#
|
38
|
-
# @example (see Sinclair::Matchers)
|
39
35
|
# @example (see Sinclair::Matchers::AddClassMethod#to)
|
40
36
|
#
|
41
37
|
# @return [AddClassMethod] RSpec Matcher
|
@@ -45,8 +41,7 @@ class Sinclair
|
|
45
41
|
|
46
42
|
# DSL to ChangeInstanceMethod
|
47
43
|
#
|
48
|
-
# @example (see Sinclair::Matchers)
|
49
|
-
# @example (see Sinclair::Matchers::ChangeInstanceMethod#to)
|
44
|
+
# @example (see Sinclair::Matchers::ChangeInstanceMethod#on)
|
50
45
|
#
|
51
46
|
# @return [ChangeInstanceMethod] RSpec Matcher
|
52
47
|
def change_method(method_name)
|
@@ -55,8 +50,7 @@ class Sinclair
|
|
55
50
|
|
56
51
|
# DSL to ChangeClassMethod
|
57
52
|
#
|
58
|
-
# @example (see Sinclair::Matchers)
|
59
|
-
# @example (see Sinclair::Matchers::ChangeClassMethod#to)
|
53
|
+
# @example (see Sinclair::Matchers::ChangeClassMethod#on)
|
60
54
|
#
|
61
55
|
# @return [ChangeClassMethod] RSpec Matcher
|
62
56
|
def change_class_method(method_name)
|
@@ -7,6 +7,21 @@ class Sinclair
|
|
7
7
|
#
|
8
8
|
# Base class responsible for building methods
|
9
9
|
class Base
|
10
|
+
# Instantiate the class and build the method
|
11
|
+
#
|
12
|
+
# @param klass [Class] class to receive the method
|
13
|
+
# @param definition [MethodDefinition] method defined
|
14
|
+
# @param type [Symbol] type of method to be build
|
15
|
+
# - +:instance+ instance methods
|
16
|
+
# - +:class+ class methods
|
17
|
+
#
|
18
|
+
# @see #build
|
19
|
+
#
|
20
|
+
# @return [Symbol] name of the method built
|
21
|
+
def self.build(klass, definition, type:)
|
22
|
+
new(klass, definition, type: type).build
|
23
|
+
end
|
24
|
+
|
10
25
|
# @param klass [Class] class to receive the method
|
11
26
|
# @param definition [MethodDefinition] method defined
|
12
27
|
# @param type [Symbol] type of method to be build
|
@@ -22,9 +37,9 @@ class Sinclair
|
|
22
37
|
#
|
23
38
|
# @return [Symbol] name of the method built
|
24
39
|
#
|
25
|
-
# @raise
|
40
|
+
# @raise NotImplementedError
|
26
41
|
def build
|
27
|
-
raise 'Not implemented yet. this should be imlemented in subclasses'
|
42
|
+
raise NotImplementedError, 'Not implemented yet. this should be imlemented in subclasses'
|
28
43
|
end
|
29
44
|
|
30
45
|
private
|
@@ -0,0 +1,49 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
class Sinclair
|
4
|
+
class MethodBuilder
|
5
|
+
# @api private
|
6
|
+
# @author darthjee
|
7
|
+
#
|
8
|
+
# Build a method based on a {MethodDefinition::CallDefinition}
|
9
|
+
class CallMethodBuilder < Base
|
10
|
+
# Builds the method
|
11
|
+
#
|
12
|
+
# The build uses +module_eval+ over a class
|
13
|
+
#
|
14
|
+
# The code is ran either on the class itself or in
|
15
|
+
# a block that allow creation of class methods
|
16
|
+
#
|
17
|
+
# @return [NilClass]
|
18
|
+
def build
|
19
|
+
evaluating_class.module_eval(&code_block)
|
20
|
+
end
|
21
|
+
|
22
|
+
private
|
23
|
+
|
24
|
+
delegate :code_block, to: :definition
|
25
|
+
# @method code_block
|
26
|
+
# @api private
|
27
|
+
# @private
|
28
|
+
#
|
29
|
+
# Code block to be evaluated by the class
|
30
|
+
#
|
31
|
+
# @return [Proc]
|
32
|
+
|
33
|
+
# Returns the klass where the proc block will be evaluated
|
34
|
+
#
|
35
|
+
# For instance type, the class itself is returned
|
36
|
+
#
|
37
|
+
# For adding class methods, the superclass is returned
|
38
|
+
#
|
39
|
+
# @return [Class]
|
40
|
+
def evaluating_class
|
41
|
+
return klass if instance?
|
42
|
+
|
43
|
+
class << klass
|
44
|
+
return self
|
45
|
+
end
|
46
|
+
end
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
@@ -10,6 +10,8 @@ class Sinclair
|
|
10
10
|
autoload :StringMethodBuilder, 'sinclair/method_builder/string_method_builder'
|
11
11
|
autoload :BlockMethodBuilder, 'sinclair/method_builder/block_method_builder'
|
12
12
|
|
13
|
+
autoload :CallMethodBuilder, 'sinclair/method_builder/call_method_builder'
|
14
|
+
|
13
15
|
CLASS_METHOD = :class
|
14
16
|
INSTANCE_METHOD = :instance
|
15
17
|
|
@@ -23,11 +25,13 @@ class Sinclair
|
|
23
25
|
# @param definitions [MethodDefinitions] all methods
|
24
26
|
# definitions to be built
|
25
27
|
# @param type [Symbol] type of method to be built
|
28
|
+
# - {CLASS_METHOD} : A class method will be built
|
29
|
+
# - {INSTANCE_METHOD} : An instance method will be built
|
26
30
|
#
|
27
31
|
# @return [MethodDefinitions]
|
28
32
|
def build_methods(definitions, type)
|
29
33
|
definitions.each do |definition|
|
30
|
-
|
34
|
+
definition.build(klass, type)
|
31
35
|
end
|
32
36
|
end
|
33
37
|
|
@@ -41,21 +45,5 @@ class Sinclair
|
|
41
45
|
# class to receive the method
|
42
46
|
#
|
43
47
|
# @return [Class]
|
44
|
-
|
45
|
-
# @private
|
46
|
-
#
|
47
|
-
# Build one method from definition
|
48
|
-
#
|
49
|
-
# @param definition [MethodDefinition] the method definition
|
50
|
-
# @param type [Symbol] type of method to be built
|
51
|
-
#
|
52
|
-
# @return (see Base#build)
|
53
|
-
def build_from_definition(definition, type)
|
54
|
-
if definition.string?
|
55
|
-
StringMethodBuilder.new(klass, definition, type: type).build
|
56
|
-
else
|
57
|
-
BlockMethodBuilder.new(klass, definition, type: type).build
|
58
|
-
end
|
59
|
-
end
|
60
48
|
end
|
61
49
|
end
|
@@ -7,6 +7,8 @@ class Sinclair
|
|
7
7
|
#
|
8
8
|
# Define a method from block
|
9
9
|
class BlockDefinition < MethodDefinition
|
10
|
+
build_with MethodBuilder::BlockMethodBuilder
|
11
|
+
|
10
12
|
# @param name [String,Symbol] name of the method
|
11
13
|
# @param block [Proc] block with code to be added as method
|
12
14
|
# @param options [Hash] Options of construction
|