classx 0.0.2 → 0.0.3

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.
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