dynamic_attributes 1.0.1 → 1.1.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -1,11 +1,34 @@
1
1
  = dynamic_attributes
2
2
 
3
- dynamic_attributes is a gem that lets you dynamically specify attributes on ActiveRecord models, which will be serialized and
4
- deserialized to a given text column.
3
+ dynamic_attributes is a gem that lets you dynamically specify attributes on ActiveRecord models, which will be serialized and deserialized to a given text column. Example:
4
+
5
+ >> dm = DynamicModel.new(:field_test => 'I am a dynamic attribute')
6
+ +-------+-------------+--------------------------------------------+
7
+ | title | description | dynamic_attributes |
8
+ +-------+-------------+--------------------------------------------+
9
+ | | | {"field_test"=>"I am a dynamic_attribute"} |
10
+ +-------+-------------+--------------------------------------------+
11
+ >> dm.field_test
12
+ => "I am a dynamic_attribute"
13
+ >> dm.field_test2
14
+ NoMethodError: undefined method `field_test2'
15
+ >> dm.field_test2 = 'I am too!'
16
+ => 'I am too!'
17
+ >> dm.field_test2
18
+ => 'I am too!'
19
+ >> dm.save
20
+ +-------+-------------+------------------------------------------------------------------------+
21
+ | title | description | dynamic_attributes |
22
+ +-------+-------------+------------------------------------------------------------------------+
23
+ | | | {"field_test2"=>"I am too!", "field_test"=>"I am a dynamic_attribute"} |
24
+ +-------+-------------+------------------------------------------------------------------------+
25
+
26
+
27
+
5
28
 
6
29
  == Requirements
7
30
 
8
- * Rails 2.x
31
+ * Rails 2.x / 3
9
32
 
10
33
  == Installation
11
34
 
@@ -39,10 +62,22 @@ To add dynamic_attributes to an AR model, take the following steps:
39
62
  - New: DynamicModel.new(:title => 'Hello', :field_summary => 'This is a dynamic attribute')
40
63
  - Create: DynamicModel.create(:title => 'Hello', :field_summary => 'This is a dynamic attribute')
41
64
  - Update:
42
- * dynamic_model.update_atribute(:field_summary, 'This is a dynamic attribute')
43
- * dynamic_model.update_atributes(:field_summary => 'This is a dynamic attribute', :description => 'Testing')
65
+ * dynamic_model.update_attribute(:field_summary, 'This is a dynamic attribute')
66
+ * dynamic_model.update_attributes(:field_summary => 'This is a dynamic attribute', :description => 'Testing')
44
67
  - Set manually: dynamic_model.field_summary = 'This is a dynamic attribute'
45
68
 
69
+ Note that a dynamic attribute should be prefixed (by default with 'field_'), see the Options section for more info.
70
+
71
+ * Get Info:
72
+ * dynamic_model.persisting_dynamic_attributes
73
+ * Returns an array of the dynamic attributes that will be persisted.
74
+ * DynamicModel.dynamic_attribute_field
75
+ * Returns the serialization attribute. You can access this serialization attribute directly if you need to.
76
+ * DynamicModel.dynamic_attribute_prefix
77
+ * Returns the method prefix of dynamic attributes, see below for more info.
78
+ * DynamicModel.destroy_dynamic_attribute_for_nil
79
+ * Returns whether dynamic attributes with null values will be persisted, see below for more info.
80
+
46
81
  == Options
47
82
 
48
83
  The has_dynamic_attribute call takes three different options:
data/Rakefile CHANGED
@@ -5,9 +5,9 @@ begin
5
5
  require 'jeweler'
6
6
  Jeweler::Tasks.new do |gem|
7
7
  gem.name = "dynamic_attributes"
8
- gem.summary = %Q{Dynamic attributes is a gem that lets you dynamically specify attributes on ActiveRecord models, which will be serialized and
8
+ gem.summary = %Q{dynamic_attributes is a gem that lets you dynamically specify attributes on ActiveRecord models, which will be serialized and
9
9
  deserialized to a given text column.}
10
- gem.description = %Q{Dynamic attributes is a gem that lets you dynamically specify attributes on ActiveRecord models, which will be serialized and
10
+ gem.description = %Q{dynamic_attributes is a gem that lets you dynamically specify attributes on ActiveRecord models, which will be serialized and
11
11
  deserialized to a given text column. Dynamic attributes can be defined by simply setting an attribute or by passing them on create or update.}
12
12
  gem.email = "r.j.delange@nedforce.nl"
13
13
  gem.homepage = "http://github.com/moiristo/dynamic_attributes"
data/VERSION CHANGED
@@ -1 +1 @@
1
- 1.0.1
1
+ 1.1.0
@@ -18,16 +18,24 @@ class << ActiveRecord::Base
18
18
  self.dynamic_attribute_prefix = options[:dynamic_attribute_prefix] || 'field_'
19
19
  cattr_accessor :destroy_dynamic_attribute_for_nil
20
20
  self.destroy_dynamic_attribute_for_nil = options[:destroy_dynamic_attribute_for_nil] || false
21
-
22
- include DynamicAttributes
21
+
22
+ include DynamicAttributes
23
23
  end
24
24
  end
25
25
 
26
26
  # The DynamicAttributes module handles all dynamic attributes.
27
27
  module DynamicAttributes
28
-
28
+
29
+ # Overrides the initializer to take dynamic attributes into account
30
+ def initialize(attributes = nil)
31
+ dynamic_attributes = {}
32
+ (attributes ||= {}).each{|att,value| dynamic_attributes[att] = value if att.to_s.starts_with?(self.dynamic_attribute_prefix) }
33
+ super(attributes.except(*dynamic_attributes.keys))
34
+ set_dynamic_attributes(dynamic_attributes)
35
+ end
36
+
29
37
  # On saving an AR record, the attributes to be persisted are re-evaluated and written to the serialization field.
30
- def before_save
38
+ def evaluate_dynamic_attributes
31
39
  new_dynamic_attributes = {}
32
40
  self.persisting_dynamic_attributes.uniq.each do |dynamic_attribute|
33
41
  value = send(dynamic_attribute)
@@ -40,24 +48,14 @@ module DynamicAttributes
40
48
  end
41
49
  write_attribute(self.dynamic_attribute_field, new_dynamic_attributes)
42
50
  end
43
-
51
+
44
52
  # After find, populate the dynamic attributes and create accessors
45
- def after_find
53
+ def populate_dynamic_attributes
46
54
  (read_attribute(self.dynamic_attribute_field) || {}).each {|att, value| set_dynamic_attribute(att, value); self.destroy_dynamic_attribute_for_nil = false if value.nil? }
47
55
  end
48
-
49
- # Creates an accessor when a non-existing setter with the configured dynamic attribute prefix is detected. Calls super otherwise.
50
- def method_missing(method, *arguments, &block)
51
- (method.to_s =~ /#{self.dynamic_attribute_prefix}(.+)=/) ? set_dynamic_attribute(self.dynamic_attribute_prefix + $1, *arguments.first) : super
52
- end
53
56
 
54
- # Overrides the initializer to take dynamic attributes into account
55
- def initialize(attributes = nil)
56
- dynamic_attributes = {}
57
- (attributes ||= {}).each{|att,value| dynamic_attributes[att] = value if att.to_s.starts_with?(self.dynamic_attribute_prefix) }
58
- super(attributes.except(*dynamic_attributes.keys))
59
- set_dynamic_attributes(dynamic_attributes)
60
- end
57
+ # Explicitly define after_find for Rails 2.x
58
+ def after_find; populate_dynamic_attributes end
61
59
 
62
60
  # Overrides update_attributes to take dynamic attributes into account
63
61
  def update_attributes(attributes)
@@ -65,6 +63,11 @@ module DynamicAttributes
65
63
  super(attributes)
66
64
  end
67
65
 
66
+ # Creates an accessor when a non-existing setter with the configured dynamic attribute prefix is detected. Calls super otherwise.
67
+ def method_missing(method, *arguments, &block)
68
+ (method.to_s =~ /#{self.dynamic_attribute_prefix}(.+)=/) ? set_dynamic_attribute(self.dynamic_attribute_prefix + $1, *arguments.first) : super
69
+ end
70
+
68
71
  # Returns the dynamic attributes that will be persisted to the serialization column. This array can
69
72
  # be altered to force dynamic attributes to not be saved in the database or to persist other attributes, but
70
73
  # it is recommended to not change it at all.
@@ -74,6 +77,9 @@ module DynamicAttributes
74
77
 
75
78
  # Ensures the configured dynamic attribute field is serialized by AR.
76
79
  def self.included object
80
+ super
81
+ object.after_find :populate_dynamic_attributes
82
+ object.before_save :evaluate_dynamic_attributes
77
83
  object.serialize object.dynamic_attribute_field
78
84
  end
79
85
 
@@ -5,6 +5,7 @@ $LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
5
5
  $LOAD_PATH.unshift(File.dirname(__FILE__))
6
6
 
7
7
  gem "activerecord"
8
+ require 'FileUtils'
8
9
  require 'active_record'
9
10
  require 'dynamic_attributes'
10
11
  require 'pp'
@@ -15,7 +16,7 @@ end
15
16
 
16
17
  def load_schema
17
18
  config = YAML::load(IO.read(File.dirname(__FILE__) + '/database.yml'))
18
- ActiveRecord::Base.logger = Logger.new(File.dirname(__FILE__) + "/debug.log")
19
+ ActiveRecord::Base.logger = ActiveSupport::BufferedLogger.new(File.dirname(__FILE__) + "/debug.log")
19
20
  db_adapter = ENV['DB']
20
21
  # no db passed, try one of these fine config-free DBs before bombing.
21
22
  db_adapter ||= begin
@@ -77,7 +77,7 @@ class TestDynamicAttributes < Test::Unit::TestCase
77
77
  def test_should_allow_different_serialization_field
78
78
  DynamicModel.dynamic_attribute_field = 'extra'
79
79
  @dynamic_model.update_attributes(:title => 'Title', :field_test1 => 'Hello', :field_test2 => 'World')
80
- assert_equal({}, @dynamic_model.dynamic_attributes)
80
+ assert_equal({}, @dynamic_model.dynamic_attributes || {})
81
81
  assert_equal({"field_test1"=>"Hello", "field_test2"=>"World"}, @dynamic_model.extra)
82
82
  end
83
83
  end
metadata CHANGED
@@ -4,9 +4,9 @@ version: !ruby/object:Gem::Version
4
4
  prerelease: false
5
5
  segments:
6
6
  - 1
7
- - 0
8
7
  - 1
9
- version: 1.0.1
8
+ - 0
9
+ version: 1.1.0
10
10
  platform: ruby
11
11
  authors:
12
12
  - Reinier de Lange
@@ -14,12 +14,12 @@ autorequire:
14
14
  bindir: bin
15
15
  cert_chain: []
16
16
 
17
- date: 2010-07-29 00:00:00 +02:00
17
+ date: 2010-09-07 00:00:00 +02:00
18
18
  default_executable:
19
19
  dependencies: []
20
20
 
21
21
  description: |-
22
- Dynamic attributes is a gem that lets you dynamically specify attributes on ActiveRecord models, which will be serialized and
22
+ dynamic_attributes is a gem that lets you dynamically specify attributes on ActiveRecord models, which will be serialized and
23
23
  deserialized to a given text column. Dynamic attributes can be defined by simply setting an attribute or by passing them on create or update.
24
24
  email: r.j.delange@nedforce.nl
25
25
  executables: []
@@ -67,7 +67,7 @@ rubyforge_project:
67
67
  rubygems_version: 1.3.6
68
68
  signing_key:
69
69
  specification_version: 3
70
- summary: Dynamic attributes is a gem that lets you dynamically specify attributes on ActiveRecord models, which will be serialized and deserialized to a given text column.
70
+ summary: dynamic_attributes is a gem that lets you dynamically specify attributes on ActiveRecord models, which will be serialized and deserialized to a given text column.
71
71
  test_files:
72
72
  - test/helper.rb
73
73
  - test/test_dynamic_attributes.rb