jeffp-enumerated_attribute 0.1.0 → 0.1.1
Sign up to get free protection for your applications and to get access to all the features.
- data/CHANGELOG.rdoc +8 -2
- data/README.rdoc +2 -2
- data/Rakefile +12 -2
- data/lib/enumerated_attribute.rb +34 -10
- data/spec/car_spec.rb +1 -1
- data/spec/tractor.rb +4 -1
- data/spec/tractor_spec.rb +29 -1
- metadata +1 -1
data/CHANGELOG.rdoc
CHANGED
@@ -1,6 +1,12 @@
|
|
1
1
|
== master
|
2
2
|
|
3
|
-
== 0.1.
|
3
|
+
== 0.1.1 / 2009-07-09
|
4
|
+
|
5
|
+
* Added enum_attr_reader and enum_attr_writer
|
6
|
+
* Added option :nil=>true to allow attributes set to nil
|
7
|
+
* Added #{attr_name}_nil? method for testing nil case
|
8
|
+
|
9
|
+
== 0.1.0 / 2009-07-08
|
4
10
|
|
5
11
|
* Added dynamic predicate method generation
|
6
12
|
* Added options handling
|
@@ -8,4 +14,4 @@
|
|
8
14
|
* Added enumeration accessor
|
9
15
|
* Added accessor and enumeration value definition
|
10
16
|
* Added simple attribute initialization
|
11
|
-
* Added DSL for short-hand method definition
|
17
|
+
* Added DSL for short-hand method definition
|
data/README.rdoc
CHANGED
@@ -82,7 +82,7 @@ demonstrated below using the Tractor class defined above:
|
|
82
82
|
t.gear_previous # => :reverse
|
83
83
|
t.gear_previous # => :over_drive
|
84
84
|
|
85
|
-
The plugin has defined +gear+ and
|
85
|
+
The plugin has defined +gear+ and gear= accessors for the attribute. They can be used
|
86
86
|
to set the attribute to one of the defined enumeration values. Attempting to set the
|
87
87
|
attribute to something besides a defined enumeration value raises an ArgumentError.
|
88
88
|
|
@@ -99,7 +99,7 @@ of the enumeration array. For example:
|
|
99
99
|
==== Using Attribute Predicates
|
100
100
|
|
101
101
|
Attribute predicates are methods used to query the state of the attribute,
|
102
|
-
for instance,
|
102
|
+
for instance, gear_is_neutral? is a predicate method for the gear attribute.
|
103
103
|
The plugin will evaluate and respond to predicate methods
|
104
104
|
for any attribute defined with it. Predicate methods are not pre-generated. By
|
105
105
|
adhering to a specific format, the plugin can recognize attribute predicates
|
data/Rakefile
CHANGED
@@ -5,7 +5,7 @@ require 'rake/contrib/sshpublisher'
|
|
5
5
|
|
6
6
|
spec = Gem::Specification.new do |s|
|
7
7
|
s.name = 'enumerated_attribute'
|
8
|
-
s.version = '0.1.
|
8
|
+
s.version = '0.1.1'
|
9
9
|
s.platform = Gem::Platform::RUBY
|
10
10
|
s.description = 'A enumerated attribute accessor'
|
11
11
|
s.summary = 'Defines enumerated attributes, initial state and dynamic state methods.'
|
@@ -28,8 +28,9 @@ require 'spec/rake/spectask'
|
|
28
28
|
|
29
29
|
namespace :spec do
|
30
30
|
desc "Run all specs"
|
31
|
-
Spec::Rake::SpecTask.new(
|
31
|
+
Spec::Rake::SpecTask.new(:test) do |t|
|
32
32
|
t.spec_files = FileList['spec/**/*_spec.rb']
|
33
|
+
t.libs << 'lib' << 'spec'
|
33
34
|
#t.spec_opts = ['--options', 'spec/spec.opts']
|
34
35
|
t.rcov = false
|
35
36
|
#t.rcov_dir = 'coverage'
|
@@ -37,6 +38,15 @@ namespace :spec do
|
|
37
38
|
end
|
38
39
|
end
|
39
40
|
|
41
|
+
desc "Run test"
|
42
|
+
Spec::Rake::SpecTask.new(:test) do |t|
|
43
|
+
t.spec_files = FileList['spec/**/*_spec.rb']
|
44
|
+
t.libs << 'lib' << 'spec'
|
45
|
+
#t.spec_opts = ['--options', 'spec/spec.opts']
|
46
|
+
t.rcov = false
|
47
|
+
#t.rcov_dir = 'coverage'
|
48
|
+
#t.rcov_opts = ['--exclude', "kernel,load-diff-lcs\.rb,instance_exec\.rb,lib/spec.rb,lib/spec/runner.rb,^spec/*,bin/spec,examples,/gems,/Library/Ruby,\.autotest,#{ENV['GEM_HOME']}"]
|
49
|
+
end
|
40
50
|
|
41
51
|
=begin
|
42
52
|
desc "Test the #{spec.name} plugin."
|
data/lib/enumerated_attribute.rb
CHANGED
@@ -1,10 +1,25 @@
|
|
1
1
|
module EnumeratedAttribute
|
2
2
|
|
3
3
|
#todo: system wide constants
|
4
|
-
#todo: allow nil
|
5
4
|
#todo: setter_callback
|
6
5
|
#todo: ArgumentError may need to use Errors for ActiveRecord
|
6
|
+
#todo: test new chaining plays nice
|
7
7
|
|
8
|
+
def enum_attr_reader(*args, &block)
|
9
|
+
if args.length > 1
|
10
|
+
args << {} if args.length == 2
|
11
|
+
args[2][:writer] = false if args[2].kind_of?(Hash)
|
12
|
+
end
|
13
|
+
enumerated_attribute(*args, &block)
|
14
|
+
end
|
15
|
+
def enum_attr_writer(*args, &block)
|
16
|
+
if args.length > 1
|
17
|
+
args << {} if args.length == 2
|
18
|
+
args[2][:reader] = false if args[2].kind_of?(Hash)
|
19
|
+
end
|
20
|
+
enumerated_attribute(*args, &block)
|
21
|
+
end
|
22
|
+
|
8
23
|
def enumerated_attribute(*args, &block)
|
9
24
|
return if args.empty?
|
10
25
|
attr_name = args[0].to_s
|
@@ -35,13 +50,15 @@ module EnumeratedAttribute
|
|
35
50
|
end
|
36
51
|
|
37
52
|
#create accessors
|
38
|
-
attr_reader attr_sym
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
53
|
+
attr_reader attr_sym unless (opts.key?(:reader) && !opts[:reader])
|
54
|
+
unless (opts.key?(:writer) && !opts[:writer])
|
55
|
+
if enums.empty?
|
56
|
+
attr_writer attr_sym
|
57
|
+
else
|
58
|
+
enumerated_attr_writer(attr_sym, opts[:nil] || false)
|
59
|
+
end
|
43
60
|
end
|
44
|
-
|
61
|
+
|
45
62
|
#define dynamic methods in method_missing
|
46
63
|
class_eval <<-METHOD
|
47
64
|
unless @missing_method_for_enumerated_attribute_defined
|
@@ -133,6 +150,9 @@ module EnumeratedAttribute
|
|
133
150
|
index = z.index(@#{attr_name})
|
134
151
|
@#{attr_name} = z[index > 0 ? index-1 : z.size-1]
|
135
152
|
end
|
153
|
+
def #{attr_name}_nil?
|
154
|
+
@#{attr_name} == nil
|
155
|
+
end
|
136
156
|
ENUM
|
137
157
|
end
|
138
158
|
|
@@ -171,12 +191,16 @@ module EnumeratedAttribute
|
|
171
191
|
|
172
192
|
private
|
173
193
|
|
174
|
-
def enumerated_attr_writer name
|
194
|
+
def enumerated_attr_writer name, allow_nil=false
|
175
195
|
name = name.to_s
|
176
196
|
class_eval <<-METHOD
|
177
|
-
def #{name}=(val)
|
197
|
+
def #{name}=(val)
|
178
198
|
val = val.to_sym if val.instance_of?(String)
|
179
|
-
|
199
|
+
unless (val == nil && #{allow_nil})
|
200
|
+
raise(ArgumentError,
|
201
|
+
(val == nil ? "nil is not allowed on #{name} attribute, set :nil=>true option" : "'" + val.to_s + "' is not an enumeration value for #{name} attribute"),
|
202
|
+
caller) unless @@enumerated_attribute_values[:#{name}].include?(val)
|
203
|
+
end
|
180
204
|
@#{name} = val
|
181
205
|
end
|
182
206
|
METHOD
|
data/spec/car_spec.rb
CHANGED
data/spec/tractor.rb
CHANGED
@@ -19,7 +19,7 @@ class Tractor
|
|
19
19
|
downshift { self.driving? ? self.gear_previous : self.gear }
|
20
20
|
end
|
21
21
|
|
22
|
-
enum_attr :plow, %w(^up down) do
|
22
|
+
enum_attr :plow, %w(^up down), :nil=>true do
|
23
23
|
plowing? { self.gear_is_in_first? && self.plow == :down }
|
24
24
|
end
|
25
25
|
|
@@ -34,5 +34,8 @@ class Tractor
|
|
34
34
|
incrementor :side_light_up
|
35
35
|
decrementor :side_light_down
|
36
36
|
end
|
37
|
+
|
38
|
+
enum_attr_reader :temperature, %w(low med high)
|
39
|
+
enum_attr_writer :ignition, %w(^off activate)
|
37
40
|
|
38
41
|
end
|
data/spec/tractor_spec.rb
CHANGED
@@ -1,7 +1,35 @@
|
|
1
|
-
require '
|
1
|
+
require 'tractor'
|
2
2
|
|
3
3
|
describe "Tractor" do
|
4
|
+
it "should have getter but no setter for :temperature" do
|
5
|
+
Tractor.instance_methods.should_not include('temperature=')
|
6
|
+
Tractor.instance_methods.should include('temperature')
|
7
|
+
end
|
8
|
+
|
9
|
+
it "should have setter but no getter for :ignition" do
|
10
|
+
Tractor.instance_methods.should_not include('ignition')
|
11
|
+
Tractor.instance_methods.should include('ignition=')
|
12
|
+
end
|
4
13
|
|
14
|
+
it "should be able to set :plow to nil" do
|
15
|
+
t=Tractor.new
|
16
|
+
lambda { t.plow = nil }.should_not raise_error(ArgumentError)
|
17
|
+
end
|
18
|
+
|
19
|
+
it "should have method :plow_nil? that operates correctly" do
|
20
|
+
t=Tractor.new
|
21
|
+
t.plow.should_not be_nil
|
22
|
+
t.plow_nil?.should be_false
|
23
|
+
t.plow = nil
|
24
|
+
t.plow.should be_nil
|
25
|
+
t.plow_nil?.should be_true
|
26
|
+
end
|
27
|
+
|
28
|
+
it "should raise ArgumentError when setting :gear to nil" do
|
29
|
+
t=Tractor.new
|
30
|
+
lambda{ t.gear = nil }.should raise_error(ArgumentError)
|
31
|
+
end
|
32
|
+
|
5
33
|
it "should have respond_to? method for :gear_is_in_neutral?" do
|
6
34
|
t=Tractor.new
|
7
35
|
t.respond_to?('gear_is_in_neutral?').should be_true
|