inherits_from 0.0.1

Sign up to get free protection for your applications and to get access to all the features.
data/Gemfile ADDED
@@ -0,0 +1,10 @@
1
+ source "http://rubygems.org"
2
+
3
+ # Specify your gem's dependencies in pseudo_inheritance.gemspec
4
+ gemspec
5
+
6
+ gem 'rake'
7
+
8
+ group :test do
9
+ gem 'rspec', '2.8.0'
10
+ end
data/README.rdoc ADDED
@@ -0,0 +1,41 @@
1
+ = inherits_from - A gem that provides an inheritance interface for ActiveRecord Models
2
+
3
+ == Introduction
4
+ inherits_from address the different paradigms between OO and RDBMS to allow ActiveRecord(AR)
5
+ objects to inherit from AR objects. Both systems have objects with Behavior, Identity & State.
6
+ OO objects that inherit from each other should have direct access to all superclasses' behavior
7
+ identity and state. RDBMS entities relate to each other. RDBMS entries should normalize
8
+ state across multiple tables. Because AR stores state in RDBMS, objects that should
9
+ inherit from other AR objects are required to use composition.
10
+
11
+ inherits_from provides an interface that allows ActiveRecord models to access other
12
+ ActiveRecord models as though they were subclassed, while allowing data to be stored
13
+ in a normalized RDBMS.
14
+
15
+ == Resources
16
+
17
+ === Installation
18
+
19
+ gem install inherits_from
20
+
21
+ === Git Repository
22
+ https://github.com/itchy/inherits_from
23
+
24
+ == Requirements
25
+ inherits_from requires ActiveRecord
26
+
27
+ === Example
28
+ class User < ActiveRecord::Base
29
+ has_many :profiles
30
+ # has an attribute of email
31
+ end
32
+
33
+ class Profile < ActiveRecord::Base
34
+ extend InheritsFrom::ClassMethods
35
+ inherits_from :user # this would be belongs_to if not using inherits_from
36
+ end
37
+
38
+ p = Profile.first
39
+ p.email => provides p.user.email
40
+ p.email="new@email.com" => sets the value of p.user.email
41
+ p.save => will also save p.user if it is tainted?
data/Rakefile ADDED
@@ -0,0 +1 @@
1
+ require "bundler/gem_tasks"
@@ -0,0 +1,26 @@
1
+ # -*- encoding: utf-8 -*-
2
+ $:.push File.expand_path("../lib", __FILE__)
3
+ require "inherits_from/version"
4
+
5
+ Gem::Specification.new do |s|
6
+ s.name = "inherits_from"
7
+ s.version = InheritsFrom::VERSION
8
+ s.authors = ["Scott Johnson"]
9
+ s.email = ["7.scott.j@gmail.com"]
10
+ s.homepage = "https://github.com/itchy/inherits_from"
11
+ s.summary = %q{ gem that provides an inheritance interface for ActiveRecord Models}
12
+ s.description = %q{inherits_from provides an interface that allows ActiveRecord models to access other
13
+ ActiveRecord models as though they were subclassed, while allowing data to be stored
14
+ in a normalized RDBMS.}
15
+
16
+ s.rubyforge_project = "inherits_from"
17
+
18
+ s.files = `git ls-files`.split("\n")
19
+ s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
20
+ s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
21
+ s.require_paths = ["lib"]
22
+
23
+ # specify any dependencies here; for example:
24
+ s.add_development_dependency "rspec"
25
+ s.add_runtime_dependency "activerecord"
26
+ end
@@ -0,0 +1,59 @@
1
+ require "inherits_from/version"
2
+
3
+ module InheritsFrom
4
+ module ClassMethods
5
+ def inherits_from(inheriter, args={})
6
+ belongs_to inheriter, args
7
+ inherited_methods(inheriter)
8
+ inherited_save(inheriter)
9
+ inherited_respond_to(inheriter)
10
+ end
11
+
12
+ private
13
+ def inherited_methods(inheriter)
14
+ define_method("method_missing") do |method, *args, &block|
15
+ @memoized_references ||= {}
16
+ @memoized_references[inheriter.to_sym] ||= self.send inheriter
17
+ model = @memoized_references[inheriter.to_sym]
18
+
19
+ if model.send :respond_to?, method
20
+ if method.to_s[/=$/]
21
+ model.send :taint
22
+ model.send method, *args
23
+ else
24
+ model.send method
25
+ end
26
+ else
27
+ super(method, *args, &block)
28
+ end
29
+ end
30
+ end
31
+
32
+ def inherited_save(inheriter)
33
+ save_methods = %w(save save!)
34
+ save_methods.each do |method|
35
+ define_method(method) do
36
+ # only momoized models need to be checked
37
+ if @memoized_references
38
+ @memoized_references.each_pair do |key, model|
39
+ model.send method if model.send :tainted?
40
+ end
41
+ end
42
+ super()
43
+ end
44
+ end
45
+ end
46
+
47
+ def inherited_respond_to(inheriter)
48
+ define_method("respond_to?") do |*args|
49
+ method = args[0]
50
+ include_private = args[1] ||= false
51
+ return true if super(method, include_private)
52
+ model = self.send inheriter
53
+ model.respond_to?(method, include_private)
54
+ end
55
+ end
56
+ end
57
+ end
58
+
59
+
@@ -0,0 +1,3 @@
1
+ module InheritsFrom
2
+ VERSION = "0.0.1"
3
+ end
data/spec/.DS_Store ADDED
Binary file
@@ -0,0 +1,55 @@
1
+ require 'spec_helper'
2
+
3
+ class User
4
+ attr_accessor :user_field
5
+ def initialize
6
+ self.user_field = "User Field"
7
+ end
8
+ end
9
+
10
+ class Profile
11
+ extend InheritsFrom::ClassMethods
12
+ # rewrite inherits_from to not use belongs_to
13
+ def self.inherits_from(inheriter, args={})
14
+ inherited_methods(inheriter)
15
+ inherited_save(inheriter)
16
+ inherited_respond_to(inheriter)
17
+ end
18
+ attr_accessor :profile_field, :user
19
+ inherits_from :user
20
+
21
+ def initialize
22
+ self.user = User.new
23
+ self.profile_field = "Profile Field"
24
+ end
25
+ end
26
+
27
+
28
+ describe Profile do
29
+ before(:each) do
30
+ @p = Profile.new
31
+ end
32
+
33
+ it "should have inherits_from, inherited_methods, inherited_save & inherited_respond_to methods" do
34
+ Profile.methods.include?(:inherits_from).should be_true
35
+ Profile.private_methods.include?(:inherited_methods).should be_true
36
+ Profile.private_methods.include?(:inherited_save).should be_true
37
+ Profile.private_methods.include?(:inherited_respond_to).should be_true
38
+ end
39
+
40
+ it "should be able to access methods in user from profile" do
41
+ @p.user_field.should == "User Field"
42
+ end
43
+
44
+ it "should be able to access update methods in user from profile" do
45
+ @p.user_field = "Test Set User Field"
46
+ @p.user_field.should == "Test Set User Field"
47
+ end
48
+
49
+ it "should set user.tainted? to true when user attribute is set" do
50
+ @p.user.tainted?.should be_false
51
+ @p.user_field = "Test Set User Field"
52
+ @p.user.tainted?.should be_true
53
+ end
54
+
55
+ end
@@ -0,0 +1,8 @@
1
+ require 'rubygems'
2
+ require 'bundler/setup'
3
+
4
+ require 'inherits_from' # and any other gems you need
5
+
6
+ RSpec.configure do |config|
7
+ # some (optional) config here
8
+ end
metadata ADDED
@@ -0,0 +1,90 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: inherits_from
3
+ version: !ruby/object:Gem::Version
4
+ prerelease:
5
+ version: 0.0.1
6
+ platform: ruby
7
+ authors:
8
+ - Scott Johnson
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+
13
+ date: 2012-02-24 00:00:00 -06:00
14
+ default_executable:
15
+ dependencies:
16
+ - !ruby/object:Gem::Dependency
17
+ name: rspec
18
+ prerelease: false
19
+ requirement: &id001 !ruby/object:Gem::Requirement
20
+ none: false
21
+ requirements:
22
+ - - ">="
23
+ - !ruby/object:Gem::Version
24
+ version: "0"
25
+ type: :development
26
+ version_requirements: *id001
27
+ - !ruby/object:Gem::Dependency
28
+ name: activerecord
29
+ prerelease: false
30
+ requirement: &id002 !ruby/object:Gem::Requirement
31
+ none: false
32
+ requirements:
33
+ - - ">="
34
+ - !ruby/object:Gem::Version
35
+ version: "0"
36
+ type: :runtime
37
+ version_requirements: *id002
38
+ description: |-
39
+ inherits_from provides an interface that allows ActiveRecord models to access other
40
+ ActiveRecord models as though they were subclassed, while allowing data to be stored
41
+ in a normalized RDBMS.
42
+ email:
43
+ - 7.scott.j@gmail.com
44
+ executables: []
45
+
46
+ extensions: []
47
+
48
+ extra_rdoc_files: []
49
+
50
+ files:
51
+ - Gemfile
52
+ - README.rdoc
53
+ - Rakefile
54
+ - inherits_from.gemspec
55
+ - lib/inherits_from.rb
56
+ - lib/inherits_from/version.rb
57
+ - spec/.DS_Store
58
+ - spec/inherits_from/inherits_from_spec.rb
59
+ - spec/spec_helper.rb
60
+ has_rdoc: true
61
+ homepage: https://github.com/itchy/inherits_from
62
+ licenses: []
63
+
64
+ post_install_message:
65
+ rdoc_options: []
66
+
67
+ require_paths:
68
+ - lib
69
+ required_ruby_version: !ruby/object:Gem::Requirement
70
+ none: false
71
+ requirements:
72
+ - - ">="
73
+ - !ruby/object:Gem::Version
74
+ version: "0"
75
+ required_rubygems_version: !ruby/object:Gem::Requirement
76
+ none: false
77
+ requirements:
78
+ - - ">="
79
+ - !ruby/object:Gem::Version
80
+ version: "0"
81
+ requirements: []
82
+
83
+ rubyforge_project: inherits_from
84
+ rubygems_version: 1.6.2
85
+ signing_key:
86
+ specification_version: 3
87
+ summary: gem that provides an inheritance interface for ActiveRecord Models
88
+ test_files:
89
+ - spec/inherits_from/inherits_from_spec.rb
90
+ - spec/spec_helper.rb