Class: SimpleEnum::Multiple::Accessors::JoinTableAccessor
- Inherits:
-
MultipleAccessor
- Object
- Accessors::Accessor
- MultipleAccessor
- SimpleEnum::Multiple::Accessors::JoinTableAccessor
- Defined in:
- lib/simple_enum/multiple/accessors/join_table_accessor.rb
Instance Attribute Summary collapse
-
#foreign_key ⇒ Object
Returns the value of attribute foreign_key.
-
#remote_key ⇒ Object
Returns the value of attribute remote_key.
-
#table ⇒ Object
Returns the value of attribute table.
Instance Method Summary collapse
- #changed?(object) ⇒ Boolean
- #init(klass) ⇒ Object
- #scope(collection, value) ⇒ Object
- #was(object) ⇒ Object
Methods inherited from MultipleAccessor
#fetch_keys, #fetch_values, #filter_keys, #initialize, #read, #selected?, #write
Constructor Details
This class inherits a constructor from SimpleEnum::Multiple::Accessors::MultipleAccessor
Instance Attribute Details
#foreign_key ⇒ Object
Returns the value of attribute foreign_key.
7 8 9 |
# File 'lib/simple_enum/multiple/accessors/join_table_accessor.rb', line 7 def foreign_key @foreign_key end |
#remote_key ⇒ Object
Returns the value of attribute remote_key.
7 8 9 |
# File 'lib/simple_enum/multiple/accessors/join_table_accessor.rb', line 7 def remote_key @remote_key end |
#table ⇒ Object
Returns the value of attribute table.
7 8 9 |
# File 'lib/simple_enum/multiple/accessors/join_table_accessor.rb', line 7 def table @table end |
Instance Method Details
#changed?(object) ⇒ Boolean
88 89 90 |
# File 'lib/simple_enum/multiple/accessors/join_table_accessor.rb', line 88 def changed?(object) object.send(:"#{source}_changed?") end |
#init(klass) ⇒ Object
9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 |
# File 'lib/simple_enum/multiple/accessors/join_table_accessor.rb', line 9 def init(klass) klass_table_name = klass.table_name.to_s join_table_name = [klass_table_name, name.pluralize].sort.join("_").to_sym table = self.table = Arel::Table.new(join_table_name) source = self.source name = self.name foreign_key = self.foreign_key = klass_table_name.singularize.foreign_key remote_key = self.remote_key = name.singularize.foreign_key klass.class_eval do define_attribute_method source define_method source do instance_variable = instance_variable_get(:"@#{source}") return instance_variable if instance_variable sql = table.where(table[foreign_key].eq(self.id)) .project(table[remote_key]) .to_sql original_cds = ActiveRecord::Base.connection.send(:select, sql).rows.map(&:first).map(&:to_i) instance_variable_set(:"@#{source}", original_cds) end define_method :"#{source}=" do |current_cds| instance_variable = instance_variable_get(:"@#{source}") send("#{source}_will_change!") unless current_cds == instance_variable instance_variable_set(:"@#{source}", current_cds.select(&:present?).map(&:to_i)) end define_method :"update_#{source}!" do return unless send(:"#{source}_changed?") original_cds = send(:"#{source}_was") current_cds = send(source) # if any enum been removed if (original_cds - current_cds).any? delete_sql = table.where(table[foreign_key].eq(self.id)) .where(table[remote_key].in(original_cds - current_cds)) .compile_delete .to_sql ActiveRecord::Base.connection.send(:delete, delete_sql) end # if any enum been added if (current_cds - original_cds).any? insert_sql = table.create_insert.tap do |insert_manager| insert_manager.into table insert_manager.columns << table[foreign_key] insert_manager.columns << table[remote_key] values = (current_cds - original_cds).map do |id| "(#{self.id}, #{id})" end.join(", ") insert_manager.values = Arel::Nodes::SqlLiteral.new("VALUES #{values}") end.to_sql ActiveRecord::Base.connection.send(:insert, insert_sql) end instance_variable_set(:"@#{source}_was", current_cds) end define_method :"clear_#{source}!" do delete_sql = table.where(table[foreign_key].eq(self.id)) .compile_delete .to_sql ActiveRecord::Base.connection.send(:delete, delete_sql) end after_save :"update_#{source}!" after_destroy :"clear_#{source}!" end end |
#scope(collection, value) ⇒ Object
92 93 94 95 96 97 |
# File 'lib/simple_enum/multiple/accessors/join_table_accessor.rb', line 92 def scope(collection, value) join = Arel::Nodes::Group.new(table).to_sql on = collection.arel_table[collection.primary_key].eq(table[foreign_key]).to_sql collection.joins("INNER JOIN #{join} ON #{on}") .where(table[foreign_key].eq(value)) end |
#was(object) ⇒ Object
84 85 86 |
# File 'lib/simple_enum/multiple/accessors/join_table_accessor.rb', line 84 def was(object) fetch_keys(object.send(:"#{source}_was").to_a) end |