option_initializer 1.1.4 → 1.2.0
Sign up to get free protection for your applications and to get access to all the features.
- data/README.md +4 -0
- data/lib/option_initializer/version.rb +1 -1
- data/lib/option_initializer.rb +72 -59
- data/test/test_option_initializer.rb +20 -1
- metadata +2 -2
data/README.md
CHANGED
data/lib/option_initializer.rb
CHANGED
@@ -1,6 +1,66 @@
|
|
1
1
|
require "option_initializer/version"
|
2
2
|
|
3
3
|
module OptionInitializer
|
4
|
+
class OptionInitializingTemplate
|
5
|
+
attr_reader :options
|
6
|
+
alias to_h options
|
7
|
+
|
8
|
+
const_set :VALIDATORS, []
|
9
|
+
|
10
|
+
def initialize base, options, need_validation
|
11
|
+
validate options if need_validation
|
12
|
+
@base = base
|
13
|
+
@options = options
|
14
|
+
end
|
15
|
+
|
16
|
+
def new *args, &block
|
17
|
+
args = args.dup
|
18
|
+
opts = @options
|
19
|
+
|
20
|
+
# Convention. Deal with it.
|
21
|
+
if args.last.is_a?(Hash)
|
22
|
+
validate args.last
|
23
|
+
opts = opts.merge(args.last)
|
24
|
+
args.pop
|
25
|
+
else
|
26
|
+
opts = opts.dup
|
27
|
+
end
|
28
|
+
|
29
|
+
opts.instance_eval do
|
30
|
+
def option_validated?
|
31
|
+
true
|
32
|
+
end
|
33
|
+
end
|
34
|
+
args << opts
|
35
|
+
|
36
|
+
@base.new(*args, &block)
|
37
|
+
end
|
38
|
+
|
39
|
+
def merge opts
|
40
|
+
validate opts
|
41
|
+
self.class.new @base, @options.merge(opts), false
|
42
|
+
end
|
43
|
+
|
44
|
+
def validate hash
|
45
|
+
self.class.const_get(:VALIDATORS).each do |validator|
|
46
|
+
hash.each do |k, v|
|
47
|
+
validator.call k, v
|
48
|
+
end
|
49
|
+
end
|
50
|
+
end
|
51
|
+
end
|
52
|
+
|
53
|
+
module MethodCallShortcut
|
54
|
+
def method_missing sym, *args, &block
|
55
|
+
# 1.8
|
56
|
+
if @base.instance_methods.map(&:to_sym).include?(sym)
|
57
|
+
new.send sym, *args, &block
|
58
|
+
else
|
59
|
+
raise NoMethodError, "undefined method `#{sym}' for #{self}"
|
60
|
+
end
|
61
|
+
end
|
62
|
+
end
|
63
|
+
|
4
64
|
def validate_options options
|
5
65
|
raise TypeError,
|
6
66
|
"wrong argument type #{options.class} (expected Hash)" unless
|
@@ -16,67 +76,13 @@ module OptionInitializer
|
|
16
76
|
end
|
17
77
|
|
18
78
|
def self.included base
|
19
|
-
base.
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
const_set :VALIDATORS, []
|
24
|
-
|
25
|
-
def initialize base, options, need_validation
|
26
|
-
validate options if need_validation
|
27
|
-
@base = base
|
28
|
-
@options = options
|
29
|
-
end
|
30
|
-
|
31
|
-
def new *args, &block
|
32
|
-
args = args.dup
|
33
|
-
opts = @options
|
34
|
-
|
35
|
-
# Convention. Deal with it.
|
36
|
-
if args.last.is_a?(Hash)
|
37
|
-
validate args.last
|
38
|
-
opts = opts.merge(args.last)
|
39
|
-
args.pop
|
40
|
-
else
|
41
|
-
opts = opts.dup
|
42
|
-
end
|
43
|
-
|
44
|
-
opts.instance_eval do
|
45
|
-
def option_validated?
|
46
|
-
true
|
47
|
-
end
|
48
|
-
end
|
49
|
-
args << opts
|
50
|
-
|
51
|
-
@base.new(*args, &block)
|
52
|
-
end
|
53
|
-
|
54
|
-
def merge opts
|
55
|
-
validate opts
|
56
|
-
self.class.new @base, @options.merge(opts), false
|
57
|
-
end
|
58
|
-
|
59
|
-
def validate hash
|
60
|
-
self.class.const_get(:VALIDATORS).each do |validator|
|
61
|
-
hash.each do |k, v|
|
62
|
-
validator.call k, v
|
63
|
-
end
|
64
|
-
end
|
65
|
-
end
|
66
|
-
|
67
|
-
def method_missing sym, *args, &block
|
68
|
-
# 1.8
|
69
|
-
if @base.instance_methods.map(&:to_sym).include?(sym)
|
70
|
-
new.send sym, *args, &block
|
71
|
-
else
|
72
|
-
raise NoMethodError, "undefined method `#{sym}' for #{self}"
|
73
|
-
end
|
74
|
-
end
|
75
|
-
} unless base.constants.map(&:to_sym).include?(:OptionInitializing)
|
79
|
+
unless base.constants.map(&:to_sym).include?(:OptionInitializing)
|
80
|
+
base.const_set :OptionInitializing, OptionInitializingTemplate.dup
|
81
|
+
end
|
76
82
|
|
77
83
|
base.class_eval do
|
78
84
|
class << self
|
79
|
-
[:option_initializer, :option_validator].each do |m|
|
85
|
+
[:option_initializer, :option_initializer!, :option_validator].each do |m|
|
80
86
|
undef_method(m) if method_defined?(m)
|
81
87
|
end
|
82
88
|
end
|
@@ -133,7 +139,14 @@ module OptionInitializer
|
|
133
139
|
end
|
134
140
|
end
|
135
141
|
end
|
142
|
+
|
143
|
+
def base.option_initializer! *syms
|
144
|
+
option_initializer(*syms)
|
145
|
+
oi = self.const_get(:OptionInitializing)
|
146
|
+
oi.class_eval do
|
147
|
+
include OptionInitializer::MethodCallShortcut
|
148
|
+
end
|
149
|
+
end
|
136
150
|
end
|
137
151
|
end
|
138
152
|
end
|
139
|
-
|
@@ -35,7 +35,8 @@ class MyClass2
|
|
35
35
|
@@validate_count
|
36
36
|
end
|
37
37
|
|
38
|
-
option_initializer :aaa
|
38
|
+
option_initializer! :aaa
|
39
|
+
option_initializer :bbb, :ccc
|
39
40
|
option_validator do |k, v|
|
40
41
|
@@validate_count += 1
|
41
42
|
case k
|
@@ -65,10 +66,24 @@ class MyClass2
|
|
65
66
|
end
|
66
67
|
end
|
67
68
|
|
69
|
+
class MyClass3
|
70
|
+
include OptionInitializer
|
71
|
+
option_initializer :aaa, :bbb, :ccc
|
72
|
+
|
73
|
+
def initialize options
|
74
|
+
validate_options options
|
75
|
+
end
|
76
|
+
|
77
|
+
def echo a
|
78
|
+
yield a
|
79
|
+
end
|
80
|
+
end
|
81
|
+
|
68
82
|
# Excerpt from README
|
69
83
|
class Person
|
70
84
|
include OptionInitializer
|
71
85
|
option_initializer :id, :name, :age, :greetings
|
86
|
+
option_initializer!
|
72
87
|
|
73
88
|
def initialize opts
|
74
89
|
@options = opts
|
@@ -110,6 +125,10 @@ class TestOptionInitializer < MiniTest::Unit::TestCase
|
|
110
125
|
def test_method_missing
|
111
126
|
assert_equal 2, MyClass2.aaa(1).bbb(2).num_options(true)
|
112
127
|
assert_equal 2, MyClass2.aaa(1).bbb(2).echo(1) { |a| a * 2 }
|
128
|
+
|
129
|
+
assert_raises(NoMethodError) do
|
130
|
+
MyClass3.aaa(1).bbb(2).echo(1) { |a| a * 2 }
|
131
|
+
end
|
113
132
|
end
|
114
133
|
|
115
134
|
def test_validator
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: option_initializer
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.
|
4
|
+
version: 1.2.0
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2013-03-
|
12
|
+
date: 2013-03-04 00:00:00.000000000 Z
|
13
13
|
dependencies: []
|
14
14
|
description: Object construction with method chaining
|
15
15
|
email:
|