app_attributes 0.5.0

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.
data/.gitignore ADDED
@@ -0,0 +1,4 @@
1
+ *.gem
2
+ .bundle
3
+ Gemfile.lock
4
+ pkg/*
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source "http://rubygems.org"
2
+
3
+ # Specify your gem's dependencies in app_attributes.gemspec
4
+ gemspec
data/README.md ADDED
@@ -0,0 +1,45 @@
1
+ # AppAttributes
2
+
3
+ A very simple polymorphic implementation of name-value pairs for any ActiveRecord model. The value is serialized to allow storage of ruby objects.
4
+
5
+ # Install
6
+
7
+ <pre>
8
+ sudo gem install app_attributes
9
+ </pre>
10
+
11
+ OR
12
+
13
+ <pre>
14
+ gem 'app_attributes'
15
+ bundle install
16
+ </pre>
17
+
18
+ # Usage
19
+
20
+ in your model:
21
+
22
+ <pre>
23
+ class Author < ActiveRecord::Base
24
+ include AppAttributes
25
+
26
+ ext_attribute :hat_size
27
+ # provides @author.hat_size, @author.hat_size=, @author.hat_size?
28
+ end
29
+ </pre>
30
+
31
+ # TODO
32
+
33
+ * automate migration. currently, you must manually copy/rename migration file in db/migrate
34
+ * finish tests
35
+ * specify dependencies
36
+
37
+ # Copyright and license
38
+
39
+ Copyright (c) 2011 Luke Wendling, released under the New BSD License
40
+
41
+ Contributors:
42
+
43
+ * Jeff Pihl
44
+ * Scott Robertson
45
+ * Mike Hansen
data/Rakefile ADDED
@@ -0,0 +1,2 @@
1
+ require 'bundler'
2
+ Bundler::GemHelper.install_tasks
@@ -0,0 +1,21 @@
1
+ # -*- encoding: utf-8 -*-
2
+ $:.push File.expand_path("../lib", __FILE__)
3
+ require "app_attributes/version"
4
+
5
+ Gem::Specification.new do |s|
6
+ s.name = "app_attributes"
7
+ s.version = AppAttributes::VERSION
8
+ s.platform = Gem::Platform::RUBY
9
+ s.authors = ["Luke Wendling"]
10
+ s.email = ["noreply@example.com"]
11
+ s.homepage = ""
12
+ s.summary = %q{Add simple name-value pairs to any ActiveRecord model}
13
+ s.description = %q{Add simple name-value pairs to any ActiveRecord model}
14
+
15
+ s.rubyforge_project = "app_attributes"
16
+
17
+ s.files = `git ls-files`.split("\n")
18
+ s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
19
+ s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
20
+ s.require_paths = ["lib"]
21
+ end
@@ -0,0 +1,17 @@
1
+ class CreateAppAttributes < ActiveRecord::Migration
2
+ def self.up
3
+ create_table :app_attributes do |t|
4
+ t.string :name
5
+ t.text :value
6
+ t.integer :attributable_id
7
+ t.string :attributable_type
8
+ t.timestamps
9
+ end
10
+
11
+ add_index :app_attributes, [:attributable_type, :attributable_id]
12
+ end
13
+
14
+ def self.down
15
+ drop_table :app_attributes
16
+ end
17
+ end
@@ -0,0 +1,15 @@
1
+ # polymorphic name-value pairs with serialized values
2
+ class AppAttribute < ActiveRecord::Base
3
+ # name :string
4
+ # value :text
5
+ # attributable_id :integer
6
+ # attributable_type :string
7
+ # timestamps
8
+
9
+ serialize :value
10
+
11
+ belongs_to :attributable, :polymorphic => true
12
+
13
+ validates_uniqueness_of :name, :scope => [:attributable_id, :attributable_type]
14
+ validates_presence_of :name
15
+ end
@@ -0,0 +1,3 @@
1
+ module AppAttributes
2
+ VERSION = "0.5.0"
3
+ end
@@ -0,0 +1,47 @@
1
+ require File.join(File.dirname(__FILE__), 'app_attributes', 'app_attribute')
2
+
3
+ module AppAttributes
4
+ def self.included(base)
5
+ base.class_eval do
6
+ has_many :app_attributes, :as => :attributable, :dependent => :delete_all
7
+ end
8
+ base.extend(ClassMethods)
9
+ end
10
+
11
+ # Example:
12
+ # include AppAttributes
13
+ # ext_attribute :something_extra, 'none'
14
+ # ext_attribute :something_else
15
+ #
16
+ module ClassMethods
17
+ def ext_attribute(name, default_value=nil)
18
+ define_method("#{name}") do
19
+ if self.new_record?
20
+ app_attr = app_attributes.detect{|oa| oa.name == "#{name}"}
21
+ else
22
+ app_attr = app_attributes.find(:first, :conditions => {:name => "#{name}"})
23
+ end
24
+ (app_attr && app_attr.value) || default_value
25
+ end
26
+
27
+ define_method("#{name}?") do
28
+ ! (value=send(name)).blank? && value != 'false'
29
+ end
30
+
31
+ define_method("#{name}=") do |raw_value|
32
+ new_value = raw_value == false ? 'false' : (raw_value.blank? ? default_value : raw_value)
33
+ if self.new_record?
34
+ return if new_value.blank? # fail silently if no default value and new value is blank
35
+ app_attr = app_attributes.detect{|oa| oa.name == "#{name}"}
36
+ app_attr ||= app_attributes.build(:name=>"#{name}")
37
+ app_attr.value = new_value
38
+ else
39
+ app_attr = app_attributes.find_or_create_by_name("#{name}")
40
+ # new_value = '-' if new_value.blank? # validation prevents blank value
41
+ app_attr.update_attributes(:value => new_value)
42
+ end
43
+ return app_attr.value
44
+ end
45
+ end
46
+ end
47
+ end
@@ -0,0 +1,14 @@
1
+ require 'test_helper'
2
+
3
+ class AppAttributeTest < Test::Unit::TestCase
4
+ should validate_presence_of(:name)
5
+
6
+ should "validate uniqueness of name in scope" do
7
+ name = 'Boston'
8
+ assert_difference "AppAttribute.count" do
9
+ AppAttribute.create(:name => name, :attributable_id => 1, :attributable_type => 'Author')
10
+ end
11
+ app_attr = AppAttribute.new(:name => name, :attributable_id => 1, :attributable_type => 'Author')
12
+ assert app_attr.errors.on(:name)
13
+ end
14
+ end
@@ -0,0 +1,17 @@
1
+ require 'test_helper'
2
+
3
+ class AppAttributesTest < Test::Unit::TestCase
4
+
5
+ context "when extending class attributes" do
6
+ setup do
7
+ AppAttribute.class_eval do
8
+ include AppAttributes
9
+ ext_attribute :test_attr
10
+ end
11
+ end
12
+
13
+ should "create dynamic getters and setters" do
14
+
15
+ end
16
+ end
17
+ end
File without changes
metadata ADDED
@@ -0,0 +1,66 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: app_attributes
3
+ version: !ruby/object:Gem::Version
4
+ prerelease:
5
+ version: 0.5.0
6
+ platform: ruby
7
+ authors:
8
+ - Luke Wendling
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+
13
+ date: 2011-04-20 00:00:00 Z
14
+ dependencies: []
15
+
16
+ description: Add simple name-value pairs to any ActiveRecord model
17
+ email:
18
+ - noreply@example.com
19
+ executables: []
20
+
21
+ extensions: []
22
+
23
+ extra_rdoc_files: []
24
+
25
+ files:
26
+ - .gitignore
27
+ - Gemfile
28
+ - README.md
29
+ - Rakefile
30
+ - app_attributes.gemspec
31
+ - db/migrate/create_app_attributes.rb
32
+ - lib/app_attributes.rb
33
+ - lib/app_attributes/app_attribute.rb
34
+ - lib/app_attributes/version.rb
35
+ - test/app_attribute_test.rb
36
+ - test/app_attributes_test.rb
37
+ - test/test_helper.rb
38
+ homepage: ""
39
+ licenses: []
40
+
41
+ post_install_message:
42
+ rdoc_options: []
43
+
44
+ require_paths:
45
+ - lib
46
+ required_ruby_version: !ruby/object:Gem::Requirement
47
+ none: false
48
+ requirements:
49
+ - - ">="
50
+ - !ruby/object:Gem::Version
51
+ version: "0"
52
+ required_rubygems_version: !ruby/object:Gem::Requirement
53
+ none: false
54
+ requirements:
55
+ - - ">="
56
+ - !ruby/object:Gem::Version
57
+ version: "0"
58
+ requirements: []
59
+
60
+ rubyforge_project: app_attributes
61
+ rubygems_version: 1.7.2
62
+ signing_key:
63
+ specification_version: 3
64
+ summary: Add simple name-value pairs to any ActiveRecord model
65
+ test_files: []
66
+