classx 0.0.2 → 0.0.3

Sign up to get free protection for your applications and to get access to all the features.
Files changed (36) hide show
  1. data/ChangeLog +84 -0
  2. data/README +4 -2
  3. data/Rakefile +1 -1
  4. data/bench/attribute_set.rb +56 -0
  5. data/bench/initialize.rb +59 -0
  6. data/doc/output/coverage/-Library-Ruby-Gems-gems-diff-lcs-1_1_2-lib-diff-lcs-block_rb.html +1 -1
  7. data/doc/output/coverage/-Library-Ruby-Gems-gems-diff-lcs-1_1_2-lib-diff-lcs-callbacks_rb.html +1 -1
  8. data/doc/output/coverage/-Library-Ruby-Gems-gems-diff-lcs-1_1_2-lib-diff-lcs-change_rb.html +1 -1
  9. data/doc/output/coverage/-Library-Ruby-Gems-gems-diff-lcs-1_1_2-lib-diff-lcs-hunk_rb.html +1 -1
  10. data/doc/output/coverage/-Library-Ruby-Gems-gems-diff-lcs-1_1_2-lib-diff-lcs_rb.html +1 -1
  11. data/doc/output/coverage/-Library-Ruby-Gems-gems-rcov-0_8_1_2_0-lib-rcov_rb.html +1 -1
  12. data/doc/output/coverage/index.html +27 -27
  13. data/doc/output/coverage/lib-classx-attribute_rb.html +82 -75
  14. data/doc/output/coverage/lib-classx-attributes_rb.html +101 -94
  15. data/doc/output/coverage/lib-classx-validate_rb.html +14 -11
  16. data/doc/output/coverage/lib-classx_rb.html +75 -65
  17. data/example/commandable.rb +9 -3
  18. data/lib/classx.rb +12 -2
  19. data/lib/classx/attribute.rb +10 -3
  20. data/lib/classx/attributes.rb +10 -3
  21. data/lib/classx/commandable.rb +27 -7
  22. data/lib/classx/declare.rb +12 -0
  23. data/lib/classx/role/logger.rb +70 -0
  24. data/lib/classx/validate.rb +6 -3
  25. data/spec/classx/default_option_spec.rb +16 -12
  26. data/spec/classx/handles_spec.rb +5 -2
  27. data/spec/classx/with_coerce.rb +12 -4
  28. data/spec/classx/with_extend.rb +3 -1
  29. data/spec/classx/with_include.rb +3 -1
  30. data/spec/classx/with_multiple_class_spec.rb +4 -2
  31. data/spec/classx/without_accessor_spec.rb +2 -1
  32. data/spec/classx/without_anyoption_spec.rb +3 -1
  33. data/spec/classx/writable_option_spec.rb +8 -4
  34. data/spec/classx_attributes_spec.rb +6 -1
  35. data/tasks/basic_config.rake +1 -1
  36. metadata +7 -2
data/lib/classx.rb CHANGED
@@ -1,7 +1,15 @@
1
1
  require 'classx/attribute'
2
2
  require 'classx/attributes'
3
3
 
4
- class ClassX
4
+ module ClassX
5
+ autoload :Validate, 'classx/validate'
6
+ autoload :Commandable, 'classx/commandable'
7
+ autoload :Declare, 'classx/declare'
8
+ autoload :Util, 'classx/util'
9
+ module Role
10
+ autoload :Logger, 'classx/role/logger'
11
+ end
12
+
5
13
  class InstanceException < Exception; end
6
14
  class AttrRequiredError < InstanceException; end
7
15
  class InvalidAttrArgument < InstanceException; end
@@ -9,7 +17,9 @@ class ClassX
9
17
  class OptionalAttrShouldBeWritable < Exception; end
10
18
  class RequiredAttrShouldNotHaveDefault < Exception; end
11
19
 
12
- extend Attributes
20
+ def self.included klass
21
+ klass.extend(Attributes)
22
+ end
13
23
 
14
24
  def initialize *args
15
25
  hash = before_init(*args)
@@ -1,4 +1,4 @@
1
- class ClassX
1
+ module ClassX
2
2
  class AttributeFactory
3
3
  def self.create args
4
4
  klass = Class.new
@@ -109,7 +109,11 @@ class ClassX
109
109
  when Proc
110
110
  args[:default].call(parent)
111
111
  else
112
- args[:default]
112
+ begin
113
+ args[:default].dup
114
+ rescue Exception
115
+ args[:default]
116
+ end
113
117
  end
114
118
  end
115
119
 
@@ -123,6 +127,9 @@ class ClassX
123
127
  return args[:lazy]
124
128
  end
125
129
 
130
+ define_method :inspect do
131
+ "ClassX::Attribute[#{self.config.inspect}]"
132
+ end
126
133
  end
127
134
  __send__ :extend, tmp_mod
128
135
 
@@ -168,7 +175,7 @@ class ClassX
168
175
  end
169
176
 
170
177
  define_method :inspect do
171
- "<#ClassX::Attribute #{self.class.config.inspect}:#{object_id} #{ @data.nil? ? '' : '@data=' + @data.inspect } >"
178
+ "<#ClassX::Attribute:#{object_id} #{ @data.nil? ? '@data=nil' : '@data=' + @data.inspect } config=#{self.class.config.inspect}>"
172
179
  end
173
180
  end
174
181
 
@@ -1,4 +1,4 @@
1
- class ClassX
1
+ module ClassX
2
2
  module Attributes
3
3
  ATTRIBUTE_REGEX = /\Aattribute_of:(\w+)\z/
4
4
 
@@ -18,6 +18,12 @@ class ClassX
18
18
  def define_attribute name, attribute
19
19
  klass_attribute = ClassX::AttributeFactory.create(attribute)
20
20
  mod = Module.new
21
+ begin
22
+ mod = self.const_get('ClassMethods')
23
+ rescue NameError => e
24
+ mod = Module.new
25
+ const_set('ClassMethods', mod)
26
+ end
21
27
  mod.module_eval do
22
28
  define_method "attribute_of:#{name}" do
23
29
  klass_attribute
@@ -26,7 +32,7 @@ class ClassX
26
32
  private "attribute_of:#{name}"
27
33
  end
28
34
  self.extend(mod)
29
- @__attribute_of ||= {}
35
+ @__attribute_of ||= self.attribute_of
30
36
  @__attribute_of[name] = klass_attribute
31
37
 
32
38
  define_method "attribute_of:#{name}" do
@@ -77,8 +83,9 @@ class ClassX
77
83
 
78
84
  alias has add_attribute
79
85
 
86
+ # hook for module to ClassX base class.
80
87
  def included klass
81
- klass.extend self
88
+ klass.extend(self.const_get('ClassMethods'))
82
89
  end
83
90
 
84
91
  end
@@ -2,7 +2,7 @@ require 'optparse'
2
2
 
3
3
  $ClassXCommandableMappingOf = {}
4
4
 
5
- class ClassX
5
+ module ClassX
6
6
  module Commandable
7
7
  class MissingCoerceMapping < Exception; end
8
8
 
@@ -11,25 +11,45 @@ class ClassX
11
11
  begin
12
12
  opt.banner = "#{$0} [options]"
13
13
  value_of = {}
14
- attribute_of.each do |key, val|
14
+ short_option_of = {}
15
+ attribute_of.keys.sort.each do |key|
16
+ val = attribute_of[key]
17
+ next if val.config[:no_cmd_option]
15
18
 
16
- val_format = val.value_class ? val.value_class : "VAL"
19
+ val_format = val.value_class ? "#{val.value_class}" : "VAL"
17
20
  if val.optional?
18
- val_format = "[ #{val_format} ]"
21
+ val_format = "[#{val_format}]"
22
+ end
23
+
24
+ short_option = key.split(//).first
25
+ unless short_option_of[short_option]
26
+ short_option_of[short_option] = key
19
27
  end
20
28
 
21
29
  if val.value_class
22
30
  begin
23
- opt.on("--#{key} #{val_format}", val.value_class, val.desc) {|v| value_of[key] = v }
31
+ if short_option_of[short_option] == key
32
+ opt.on("-#{short_option}", "--#{key} #{val_format}", val.value_class, val.desc) {|v| value_of[key] = v }
33
+ else
34
+ opt.on("--#{key} #{val_format}", val.value_class, val.desc) {|v| value_of[key] = v }
35
+ end
24
36
  rescue Exception => e
25
37
  if $ClassXCommandableMappingOf[val.value_class]
26
- opt.on("--#{key} #{val_format}", $ClassXCommandableMappingOf[val.value_class], val.desc) {|v| value_of[key] = v }
38
+ if short_option_of[short_option] == key
39
+ opt.on("-#{short_option}", "--#{key} #{$ClassXCommandableMappingOf[val.value_class]}", $ClassXCommandableMappingOf[val.value_class], val.desc) {|v| value_of[key] = v }
40
+ else
41
+ opt.on("--#{key} #{$ClassXCommandableMappingOf[val.value_class]}", $ClassXCommandableMappingOf[val.value_class], val.desc) {|v| value_of[key] = v }
42
+ end
27
43
  else
28
44
  raise MissingCoerceMapping, "missing coerce rule. please specify $ClassXCommandableMappingOf"
29
45
  end
30
46
  end
31
47
  else
32
- opt.on("--#{key} #{val_format}") {|v| value_of[key] = v }
48
+ if short_option_of[short_option] == key
49
+ opt.on("-#{short_option}", "--#{key} #{val_format}") {|v| value_of[key] = v }
50
+ else
51
+ opt.on("--#{key} #{val_format}") {|v| value_of[key] = v }
52
+ end
33
53
  end
34
54
  end
35
55
 
@@ -0,0 +1,12 @@
1
+ module ClassX
2
+ module Declare
3
+ def classx name, &block
4
+ klass = Class.new
5
+ klass.class_eval do
6
+ include(ClassX)
7
+ end
8
+ klass.class_eval &block
9
+ eval "::#{name.capitalize} = klass"
10
+ end
11
+ end
12
+ end
@@ -0,0 +1,70 @@
1
+ require 'logger'
2
+
3
+ module ClassX
4
+ module Role
5
+ # SYNOPSIS
6
+ #
7
+ # require 'classx/role/logger'
8
+ # class YourApp < ClassX
9
+ # extends ClassX::Commandable
10
+ # include ClassX::Role::Logger
11
+ #
12
+ # def run
13
+ # logger.debug("debug!!")
14
+ # # do something
15
+ # end
16
+ # end
17
+ #
18
+ # and run following:
19
+ #
20
+ # $ your_app.rb --logfile log/debug.log --log_level debug
21
+ #
22
+ # SEE ALSO: +ClassX::Commandable+
23
+ #
24
+ module Logger
25
+ extend ClassX::Attributes
26
+
27
+ module ToLogLevel
28
+ def to_log_level str=self.get
29
+ ::Logger::Severity.const_get(str.upcase)
30
+ end
31
+
32
+ alias to_i to_log_level
33
+ end
34
+
35
+ has :logger,
36
+ :lazy => true,
37
+ :optional => true,
38
+ :no_cmd_option => true,
39
+ :default => proc {|mine|
40
+ logger = ::Logger.new(mine.logfile)
41
+ logger.level = mine.attribute_of['log_level'].to_i
42
+ logger.progname = $0
43
+
44
+ logger
45
+ }
46
+
47
+ has :log_level,
48
+ :kind_of => String,
49
+ :desc => 'log_level (debug|info|warn|error|fatal) (default info)',
50
+ :optional => true,
51
+ :default => 'info',
52
+ :include => ToLogLevel,
53
+ :validate => proc {|val|
54
+ begin
55
+ ::Logger::Severity.const_get(val.upcase)
56
+ rescue NameError => e
57
+ return false
58
+ end
59
+ true
60
+ }
61
+
62
+ has :logfile,
63
+ :kind_of => String,
64
+ :desc => 'output logfile. (default STDERR)',
65
+ :optional => true,
66
+ :default => $stderr # hmm, is name bad?
67
+
68
+ end
69
+ end
70
+ end
@@ -5,8 +5,8 @@ module ClassX::Validate
5
5
  #
6
6
  # require 'classx/validate'
7
7
  #
8
- # class YourClass < ClassX
9
- # include Validate
8
+ # class YourClass
9
+ # include ClassX::Validate
10
10
  #
11
11
  # def run params
12
12
  # validate params do
@@ -27,7 +27,10 @@ module ClassX::Validate
27
27
  @@__validate_cached ||= {}
28
28
  uniq_key = caller[0]
29
29
  unless @@__validate_cached[uniq_key]
30
- @@__validate_cached[uniq_key] = Class.new(ClassX)
30
+ @@__validate_cached[uniq_key] = Class.new
31
+ @@__validate_cached[uniq_key].class_eval do
32
+ include ::ClassX
33
+ end
31
34
  @@__validate_cached[uniq_key].class_eval(&block)
32
35
  end
33
36
  @@__validate_cached[uniq_key].new hash
@@ -6,8 +6,9 @@ describe ClassX do
6
6
  describe 'with :default option' do
7
7
  describe 'when value is Proc' do
8
8
  before do
9
- @class = Class.new(ClassX)
9
+ @class = Class.new
10
10
  @class.class_eval do
11
+ include ClassX
11
12
  has :x, :default => proc { Object.new }
12
13
  end
13
14
  end
@@ -34,8 +35,9 @@ describe ClassX do
34
35
 
35
36
  describe 'when value is not Proc' do
36
37
  before do
37
- @class = Class.new(ClassX)
38
+ @class = Class.new
38
39
  @class.class_eval do
40
+ include ClassX
39
41
  has :x, :default => []
40
42
  end
41
43
  end
@@ -43,17 +45,14 @@ describe ClassX do
43
45
  it 'should have any value when instanciate' do
44
46
  @class.new.x.should == []
45
47
  end
46
-
47
- it 'should have the same object_id between some instance' do
48
- @class.new.x.should equal(@class.new.x)
49
- end
50
48
  end
51
49
  end
52
50
 
53
51
  describe 'with :optional is false' do
54
52
  before do
55
- @class = Class.new(ClassX)
53
+ @class = Class.new
56
54
  @class.class_eval do
55
+ include ClassX
57
56
  has :x, :optional => false
58
57
  end
59
58
  end
@@ -74,8 +73,9 @@ describe ClassX do
74
73
  describe ':optional is false and with :default option' do
75
74
  it 'should raise ClassX::RequiredAttrShouldNotHaveDefault' do
76
75
  lambda {
77
- klass = Class.new(ClassX)
76
+ klass = Class.new
78
77
  klass.class_eval do
78
+ include ClassX
79
79
  has :x, :optional => false, :default => 1
80
80
  end
81
81
  }.should raise_error(ClassX::RequiredAttrShouldNotHaveDefault)
@@ -84,8 +84,9 @@ describe ClassX do
84
84
 
85
85
  describe 'declare attribute without :optional and :default option' do
86
86
  before do
87
- @class = Class.new(ClassX)
87
+ @class = Class.new
88
88
  @class.class_eval do
89
+ include ClassX
89
90
  has :x, :kind_of => Integer
90
91
  end
91
92
  end
@@ -97,8 +98,9 @@ describe ClassX do
97
98
 
98
99
  describe ':optional is true and without :default option' do
99
100
  before do
100
- @class = Class.new(ClassX)
101
+ @class = Class.new
101
102
  @class.class_eval do
103
+ include ClassX
102
104
  has :x, :optional => true, :kind_of => Integer
103
105
  end
104
106
  end
@@ -111,8 +113,9 @@ describe ClassX do
111
113
  describe 'with :optional is true' do
112
114
  describe 'without :writable option' do
113
115
  before do
114
- @class = Class.new(ClassX)
116
+ @class = Class.new
115
117
  @class.class_eval do
118
+ include ClassX
116
119
  has :x, :optional => true
117
120
  end
118
121
  end
@@ -124,8 +127,9 @@ describe ClassX do
124
127
 
125
128
  describe 'not attribute param exist in #initialize argument' do
126
129
  before do
127
- @class = Class.new(ClassX)
130
+ @class = Class.new
128
131
  @class.class_eval do
132
+ include ClassX
129
133
  has :x
130
134
  end
131
135
  end
@@ -5,8 +5,9 @@ describe ClassX do
5
5
  describe '#has' do
6
6
  describe 'with handles option as Hash' do
7
7
  before do
8
- @class1 = Class.new(ClassX)
8
+ @class1 = Class.new
9
9
  @class1.class_eval do
10
+ include ClassX
10
11
  has :x, :handles => { :x_inspect => :inspect }
11
12
  end
12
13
  end
@@ -24,8 +25,10 @@ describe ClassX do
24
25
 
25
26
  describe 'with handles option as Array' do
26
27
  before do
27
- @class1 = Class.new(ClassX)
28
+ @class1 = Class.new
28
29
  @class1.class_eval do
30
+ include ClassX
31
+
29
32
  has :x, :handles => [ :length ]
30
33
  end
31
34
  end
@@ -6,8 +6,10 @@ describe ClassX do
6
6
  describe 'with coece' do
7
7
  describe 'when Array is value' do
8
8
  before do
9
- @class = Class.new(ClassX)
9
+ @class = Class.new
10
10
  @class.class_eval do
11
+ include ClassX
12
+
11
13
  has :x, :isa => Integer, :coerce => [
12
14
  { proc {|val| val.respond_to? :to_i } => proc {|val| val.to_i } },
13
15
  { proc {|val| val.respond_to? :to_s } => proc {|val| val.to_s } },
@@ -26,8 +28,10 @@ describe ClassX do
26
28
 
27
29
  describe 'when Proc is key' do
28
30
  before do
29
- @class = Class.new(ClassX)
31
+ @class = Class.new
30
32
  @class.class_eval do
33
+ include ClassX
34
+
31
35
  has :x, :isa => Integer, :coerce => { proc {|val| val.respond_to? :to_i } => proc {|val| val.to_i } }
32
36
  end
33
37
  end
@@ -43,8 +47,10 @@ describe ClassX do
43
47
 
44
48
  describe 'when Symbol is key' do
45
49
  before do
46
- @class = Class.new(ClassX)
50
+ @class = Class.new
47
51
  @class.class_eval do
52
+ include ClassX
53
+
48
54
  has :x, :isa => Integer, :coerce => { :to_i => proc {|val| val.to_i } }
49
55
  end
50
56
  end
@@ -60,8 +66,10 @@ describe ClassX do
60
66
 
61
67
  describe 'when Module or Class is key' do
62
68
  before do
63
- @class = Class.new(ClassX)
69
+ @class = Class.new
64
70
  @class.class_eval do
71
+ include ClassX
72
+
65
73
  has :x, :isa => Integer, :coerce => { String => proc {|val| val.to_i } }
66
74
  end
67
75
  end
@@ -5,7 +5,7 @@ describe ClassX do
5
5
  describe '#has' do
6
6
  describe 'with extend' do
7
7
  before do
8
- @class = Class.new(ClassX)
8
+ @class = Class.new
9
9
  mod = Module.new
10
10
  mod.module_eval do
11
11
  define_method :test do
@@ -13,6 +13,8 @@ describe ClassX do
13
13
  end
14
14
  end
15
15
  @class.class_eval do
16
+ include ClassX
17
+
16
18
  has :x, :extend => mod
17
19
  end
18
20
  end