has_many_polymorphic 0.5.0 → 0.6.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/README.rdoc CHANGED
@@ -6,9 +6,10 @@ This mixin adds a has many polymorphic relationship to a model and creates all t
6
6
  - Models
7
7
  - the models you want to autoload so all the relationships are created on initialzation of Rails
8
8
 
9
- == Example Usage
9
+ == Setup
10
10
 
11
- RussellEdge::HasManyPolymorphic.options[:models] = %w(PreferenceType)
11
+ You must define the models that you want to use inside an initializer using
12
+ RussellEdge::HasManyPolymorphic.add_models(%w(PreferenceType)) or RussellEdge::HasManyPolymorphic.add_models("PreferenceType")
12
13
 
13
14
  == Params
14
15
  - Name
@@ -42,7 +43,7 @@ this gives you the following
42
43
 
43
44
  and
44
45
 
45
- preferenceType.preferenced_records
46
+ preferenceType.preferenced_records
46
47
 
47
48
  which is a concatentated array of the models. You also get the following
48
49
 
@@ -0,0 +1,44 @@
1
+ module RussellEdge
2
+ module HasManyPolymorphic
3
+ class Engine < Rails::Engine
4
+ isolate_namespace HasManyPolymorphic
5
+ DEFAULT_OPTIONS = {:models => %w()}
6
+ @@options = HashWithIndifferentAccess.new(DEFAULT_OPTIONS)
7
+
8
+ initializer "has_many_polymorphic.autoload_models", :after => :load_config_initializers do |app|
9
+ RussellEdge::HasManyPolymorphic::Engine.autoload_models
10
+ end
11
+
12
+ ActiveSupport.on_load(:active_record) do
13
+ include RussellEdge::HasManyPolymorphic
14
+ end
15
+
16
+ #set engine to scope
17
+ engine = self
18
+ config.to_prepare do
19
+ engine.autoload_models
20
+ end
21
+
22
+ class << self
23
+ def add_models(models)
24
+ if models.is_a? Array
25
+ @@options[:models] = @@options[:models] | models
26
+ else
27
+ @@options[:models] << models
28
+ end
29
+ end
30
+
31
+ # Dispatcher callback to load polymorphic relationships
32
+ def autoload_models
33
+ @@options[:models].each do |model|
34
+ #try to load model if it exists.
35
+ begin
36
+ model.constantize
37
+ rescue=>e
38
+ end
39
+ end
40
+ end
41
+ end
42
+ end
43
+ end
44
+ end
@@ -1,143 +1,143 @@
1
1
  module RussellEdge #:nodoc:
2
- module HasManyPolymorphic #:nodoc:
2
+ module HasManyPolymorphic #:nodoc:
3
3
 
4
- def self.included(base)
5
- base.extend(ClassMethods)
6
- end
4
+ def self.included(base)
5
+ base.extend(ClassMethods)
6
+ end
7
7
 
8
- module ClassMethods
8
+ module ClassMethods
9
9
 
10
- ##
11
- # HasManyPolymorphic
12
- # This mixin adds a has many polymorphic relationship to a model and creates all the relationships needed
13
- # by rails to handle it.
14
- #
15
- # Params
16
- #
17
- # Name - name of the relationship, there is a convention that whatever name you choose, the polymorphic
18
- # table columns on your through table should match.
19
- #
20
- # Options
21
- # - through - the model that handles the through relationship
22
- # - models - models that should be included in this polymophic relationship
23
- #
24
- #
25
- # One method is added for you to use
26
- #
27
- # - {name param}
28
- # - the name of your relationship is used for the method name of this method. it will return
29
- # an array of the models that are related via the has_many relationships
30
- #
31
- # There is an after_save call back that will save the relationships when they are added or removed
32
- # If you want to remove a relationship the models need to be destroyed and this model reloaded.
33
- #
34
- # Example Usage
35
- #
36
- # class PreferenceType < ActiveRecord::Base
37
- # has_morpheus :preferenced_records,
38
- # :through => :valid_preference_types,
39
- # :models => [:desktops, :organizers]
40
- # end
41
- #
42
- # this gives you the following
43
- #
44
- # preferenceType = PreferenceType.first
45
- # preferenceType.desktops
46
- # preferenceType.organizers
47
- #
48
- # and
49
- #
50
- # preferenceType.preferenced_records
51
- #
52
- # which is a concatentated array of the models. You also get the following
53
- #
54
- # desktop = Desktop.first
55
- # desktop.preference_types
56
- #
57
- # organizer = Organizer.first
58
- # organizer.preference_types
59
- ##
10
+ ##
11
+ # HasManyPolymorphic
12
+ # This mixin adds a has many polymorphic relationship to a model and creates all the relationships needed
13
+ # by rails to handle it.
14
+ #
15
+ # Params
16
+ #
17
+ # Name - name of the relationship, there is a convention that whatever name you choose, the polymorphic
18
+ # table columns on your through table should match.
19
+ #
20
+ # Options
21
+ # - through - the model that handles the through relationship
22
+ # - models - models that should be included in this polymophic relationship
23
+ #
24
+ #
25
+ # One method is added for you to use
26
+ #
27
+ # - {name param}
28
+ # - the name of your relationship is used for the method name of this method. it will return
29
+ # an array of the models that are related via the has_many relationships
30
+ #
31
+ # There is an after_save call back that will save the relationships when they are added or removed
32
+ # If you want to remove a relationship the models need to be destroyed and this model reloaded.
33
+ #
34
+ # Example Usage
35
+ #
36
+ # class PreferenceType < ActiveRecord::Base
37
+ # has_morpheus :preferenced_records,
38
+ # :through => :valid_preference_types,
39
+ # :models => [:desktops, :organizers]
40
+ # end
41
+ #
42
+ # this gives you the following
43
+ #
44
+ # preferenceType = PreferenceType.first
45
+ # preferenceType.desktops
46
+ # preferenceType.organizers
47
+ #
48
+ # and
49
+ #
50
+ # preferenceType.preferenced_records
51
+ #
52
+ # which is a concatentated array of the models. You also get the following
53
+ #
54
+ # desktop = Desktop.first
55
+ # desktop.preference_types
56
+ #
57
+ # organizer = Organizer.first
58
+ # organizer.preference_types
59
+ ##
60
60
 
61
- def has_many_polymorphic(name, options = {})
62
- target_class_name = self.name
63
- instance_array_name = "#{name}_array".to_sym
61
+ def has_many_polymorphic(name, options = {})
62
+ target_class_name = self.name
63
+ instance_array_name = "#{name}_array".to_sym
64
64
 
65
- #declare array to related models
66
- attr_accessor instance_array_name
65
+ #declare array to related models
66
+ attr_accessor instance_array_name
67
67
 
68
- #create the has_many relationship
69
- has_many options[:through], :dependent => :destroy
68
+ #create the has_many relationship
69
+ has_many options[:through], :dependent => :destroy
70
70
 
71
- #create the has_many relationship for each model
71
+ #create the has_many relationship for each model
72
+ options[:models].each do |model|
73
+ has_many model, :through => options[:through], :source => model.to_s.singularize,
74
+ :conditions => ["#{options[:through]}.#{name.to_s.singularize}_type = ?", model.to_s.classify], :dependent => :destroy
75
+ end
76
+
77
+ #modify the through class to add the belongs to relationships
78
+ options[:through].to_s.classify.constantize.class_exec do
72
79
  options[:models].each do |model|
73
- has_many model, :through => options[:through], :source => model.to_s.singularize,
74
- :conditions => ["#{options[:through]}.#{name.to_s.singularize}_type = ?", model.to_s.classify], :dependent => :destroy
80
+ belongs_to model.to_s.singularize.to_sym, :class_name => model.to_s.classify, :foreign_key => "#{name.to_s.singularize}_id"
75
81
  end
82
+ end
76
83
 
77
- #modify the through class to add the belongs to relationships
78
- options[:through].to_s.classify.constantize.class_exec do
79
- options[:models].each do |model|
80
- belongs_to model.to_s.singularize.to_sym, :class_name => model.to_s.classify, :foreign_key => "#{name.to_s.singularize}_id"
81
- end
84
+ #I want to keep the << and push methods of array so this helps to keep them.
85
+ define_method name do
86
+ #used the declared instance variable array
87
+ records = self.send(instance_array_name.to_s)
88
+ records = records || []
89
+ options[:models].each do |model|
90
+ records = records | self.send(model.to_s)
82
91
  end
83
-
84
- #I want to keep the << and push methods of array so this helps to keep them.
85
- define_method name do
86
- #used the declared instance variable array
87
- records = self.send(instance_array_name.to_s)
88
- records = records || []
89
- options[:models].each do |model|
90
- records = records | self.send(model.to_s)
91
- end
92
92
 
93
- #set it back to the instance variable
94
- self.send("#{instance_array_name.to_s}=", records)
93
+ #set it back to the instance variable
94
+ self.send("#{instance_array_name.to_s}=", records)
95
95
 
96
- records
97
- end
96
+ records
97
+ end
98
98
 
99
- #before we save this model make sure you save all the relationships.
100
- before_save do |record|
101
- record.send(name).each do |reln_record|
102
- #handle STI get superclass class_name if not sub class of ActiveRecord::Base
103
- klass_name = (reln_record.class.superclass == ActiveRecord::Base) ? reln_record.class.name : reln_record.class.superclass.name
104
- conditions = "#{name.to_s.singularize}_id = #{reln_record.id} and #{name.to_s.singularize}_type = '#{klass_name}'"
105
- exisiting_record = record.send("#{options[:through]}").find(:first,:conditions => conditions)
99
+ #before we save this model make sure you save all the relationships.
100
+ before_save do |record|
101
+ record.send(name).each do |reln_record|
102
+ #handle STI get superclass class_name if not sub class of ActiveRecord::Base
103
+ klass_name = (reln_record.class.superclass == ActiveRecord::Base) ? reln_record.class.name : reln_record.class.superclass.name
104
+ conditions = "#{name.to_s.singularize}_id = #{reln_record.id} and #{name.to_s.singularize}_type = '#{klass_name}'"
105
+ exisiting_record = record.send("#{options[:through]}").find(:first,:conditions => conditions)
106
106
 
107
- if exisiting_record.nil?
108
- values_hash = {}
109
- values_hash["#{record.class.name.underscore}_id"] = record.id
110
- values_hash["#{name.to_s.singularize}_type"] = klass_name
111
- values_hash["#{name.to_s.singularize}_id"] = reln_record.id
107
+ if exisiting_record.nil?
108
+ values_hash = {}
109
+ values_hash["#{record.class.name.underscore}_id"] = record.id
110
+ values_hash["#{name.to_s.singularize}_type"] = klass_name
111
+ values_hash["#{name.to_s.singularize}_id"] = reln_record.id
112
112
 
113
- options[:through].to_s.classify.constantize.create(values_hash)
114
- end
113
+ options[:through].to_s.classify.constantize.create(values_hash)
115
114
  end
116
115
  end
116
+ end
117
117
 
118
118
  #include instance methods into this model
119
- include RussellEdge::HasManyPolymorphic::InstanceMethods
119
+ include RussellEdge::HasManyPolymorphic::InstanceMethods
120
120
 
121
- #add the relationship to the models.
122
- options[:models].each do |model|
123
- model.to_s.classify.constantize.class_exec do
124
- has_many options[:through], :as => name.to_s.singularize
125
- has_many target_class_name.tableize, :through => options[:through]
126
- end
121
+ #add the relationship to the models.
122
+ options[:models].each do |model|
123
+ model.to_s.classify.constantize.class_exec do
124
+ has_many options[:through], :as => name.to_s.singularize
125
+ has_many target_class_name.tableize, :through => options[:through]
127
126
  end
128
-
129
127
  end
128
+
130
129
  end
130
+ end
131
131
 
132
- module InstanceMethods
133
- #clear array on reload
134
- def reload(*args)
135
- @records = []
136
-
137
- super args
138
- end
132
+ module InstanceMethods
133
+ #clear array on reload
134
+ def reload(*args)
135
+ @records = []
139
136
 
137
+ super args
140
138
  end
141
139
 
142
140
  end
143
- end
141
+
142
+ end
143
+ end
@@ -1,3 +1,3 @@
1
1
  module HasManyPolymorphic
2
- VERSION = '0.5.0' unless defined?(::HasManyPolymorphic::VERSION)
2
+ VERSION = '0.6.0' unless defined?(::HasManyPolymorphic::VERSION)
3
3
  end
@@ -1,7 +1,4 @@
1
1
  require 'has_many_polymorphic/has_many_polymorphic'
2
- ActiveRecord::Base.send :include, RussellEdge::HasManyPolymorphic
3
-
4
- #used to tie into Rails initialization to load the models so the relationships are created
5
- require 'has_many_polymorphic/autoload'
2
+ require 'has_many_polymorphic/engine'
6
3
 
7
4
 
metadata CHANGED
@@ -1,87 +1,61 @@
1
- --- !ruby/object:Gem::Specification
1
+ --- !ruby/object:Gem::Specification
2
2
  name: has_many_polymorphic
3
- version: !ruby/object:Gem::Version
4
- hash: 11
5
- prerelease: false
6
- segments:
7
- - 0
8
- - 5
9
- - 0
10
- version: 0.5.0
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.6.0
5
+ prerelease:
11
6
  platform: ruby
12
- authors:
7
+ authors:
13
8
  - Russell Holmes
14
9
  autorequire:
15
10
  bindir: bin
16
11
  cert_chain: []
17
-
18
- date: 2011-08-24 00:00:00 -04:00
19
- default_executable:
20
- dependencies:
21
- - !ruby/object:Gem::Dependency
12
+ date: 2011-11-15 00:00:00.000000000Z
13
+ dependencies:
14
+ - !ruby/object:Gem::Dependency
22
15
  name: activerecord
23
- prerelease: false
24
- requirement: &id001 !ruby/object:Gem::Requirement
16
+ requirement: &2152612200 !ruby/object:Gem::Requirement
25
17
  none: false
26
- requirements:
27
- - - ">="
28
- - !ruby/object:Gem::Version
29
- hash: 9
30
- segments:
31
- - 2
32
- - 3
33
- - 5
18
+ requirements:
19
+ - - ! '>='
20
+ - !ruby/object:Gem::Version
34
21
  version: 2.3.5
35
22
  type: :runtime
36
- version_requirements: *id001
23
+ prerelease: false
24
+ version_requirements: *2152612200
37
25
  description: Simple replacement for has_many_polymorphs
38
26
  email: rholmes@tnsolutionsinc.com
39
27
  executables: []
40
-
41
28
  extensions: []
42
-
43
29
  extra_rdoc_files: []
44
-
45
- files:
46
- - lib/has_many_polymorphic/autoload.rb
30
+ files:
31
+ - lib/has_many_polymorphic/engine.rb
47
32
  - lib/has_many_polymorphic/has_many_polymorphic.rb
48
33
  - lib/has_many_polymorphic/version.rb
49
34
  - lib/has_many_polymorphic.rb
50
35
  - MIT-LICENSE.txt
51
36
  - README.rdoc
52
- has_rdoc: true
53
37
  homepage: https://github.com/russ1985/has_many_polymorphic
54
38
  licenses: []
55
-
56
39
  post_install_message:
57
40
  rdoc_options: []
58
-
59
- require_paths:
41
+ require_paths:
60
42
  - lib
61
- required_ruby_version: !ruby/object:Gem::Requirement
43
+ required_ruby_version: !ruby/object:Gem::Requirement
62
44
  none: false
63
- requirements:
64
- - - ">="
65
- - !ruby/object:Gem::Version
66
- hash: 3
67
- segments:
68
- - 0
69
- version: "0"
70
- required_rubygems_version: !ruby/object:Gem::Requirement
45
+ requirements:
46
+ - - ! '>='
47
+ - !ruby/object:Gem::Version
48
+ version: '0'
49
+ required_rubygems_version: !ruby/object:Gem::Requirement
71
50
  none: false
72
- requirements:
73
- - - ">="
74
- - !ruby/object:Gem::Version
75
- hash: 3
76
- segments:
77
- - 0
78
- version: "0"
51
+ requirements:
52
+ - - ! '>='
53
+ - !ruby/object:Gem::Version
54
+ version: '0'
79
55
  requirements: []
80
-
81
56
  rubyforge_project:
82
- rubygems_version: 1.3.7
57
+ rubygems_version: 1.8.10
83
58
  signing_key:
84
59
  specification_version: 3
85
60
  summary: Simple replacement for has_many_polymorphs
86
61
  test_files: []
87
-
@@ -1,37 +0,0 @@
1
- module RussellEdge
2
- module HasManyPolymorphic
3
-
4
- =begin rdoc
5
- Searches for models that use <tt>has_many_polymorphic</tt> and makes sure that they get loaded during app initialization.
6
- This ensures that helper methods are injected into the target classes.
7
- =end
8
-
9
- #define the models that use has_many_polymorphic. has_many_polymorphs combed the file system for models
10
- #that had the has_many_polymorphs method. This is not as robust but more efficent. It can be set via
11
- #
12
- #RussellEdge::HasManyPolymorphic::OPTIONS = { :models => %w(PreferenceType AnotherModel) }
13
- #
14
- DEFAULT_OPTIONS = {:models => %w()}
15
- mattr_accessor :options
16
- @@options = HashWithIndifferentAccess.new(DEFAULT_OPTIONS)
17
-
18
- # Dispatcher callback to load polymorphic relationships
19
- def self.autoload
20
- options[:models].each do |model|
21
- #try to load model if it exists.
22
- begin
23
- model.constantize
24
- rescue=>e
25
- end
26
- end
27
-
28
- end
29
- end
30
- end
31
-
32
- #create Railtie to plugin into rails initialization
33
- class RussellEdge::HasManyPolymorphic::RailTie < Rails::Railtie
34
- initializer "has_many_polymorphic.autoload_models", :after => :initialize do |app|
35
- RussellEdge::HasManyPolymorphic.autoload
36
- end
37
- end