module Customize::Inherited
Public Class Methods
included(base)
click to toggle source
# File lib/customize/inherited.rb, line 3 def self.included base base.extend ClassMethods base.has_one :inherit_node, :class_name=>Customize::InheritNode.name, :as=>:node, :dependent=>:destroy base.scope :ascents_for, lambda { |object, options={:include=>false}| ntn = Customize::InheritNode.table_name node = object.inherit_node condition_string = if options[:include] "#{ntn}.left <= ? and #{ntn}.right >= ?" else "#{ntn}.left < ? and #{ntn}.right > ?" end base.joins(:inherit_node).where(condition_string, node.left, node.right) } base.scope :descents_for, lambda { |object, options={:include=>false}| ntn = Customize::InheritNode.table_name node = object.inherit_node condition_string = if options[:include] "#{ntn}.left >= ? and #{ntn}.right <= ?" else "#{ntn}.left > ? and #{ntn}.right < ?" end base.joins(:inherit_node).where(condition_string, node.left, node.right) } base.after_create { |object| object.create_inherit_node } base.delegate :leaf?, :to=>:inherit_node base.before_destroy { |object| raise 'object should not have children when destroy' if object.inherit_node.children.size > 0 } end
Public Instance Methods
ascent_ids()
click to toggle source
# File lib/customize/inherited.rb, line 106 def ascent_ids ascents.map(&:id) end
ascents(options={:include=>false})
click to toggle source
# File lib/customize/inherited.rb, line 89 def ascents options={:include=>false} return [] if new_record? self.class.ascents_for self, options end
children()
click to toggle source
# File lib/customize/inherited.rb, line 69 def children inherit_node.children.collect(&:node) end
descent_ids()
click to toggle source
# File lib/customize/inherited.rb, line 110 def descent_ids descents.map(&:id) end
descents()
click to toggle source
# File lib/customize/inherited.rb, line 101 def descents return [] if new_record? self.class.descents_for self end
inherit(parent)
click to toggle source
# File lib/customize/inherited.rb, line 77 def inherit parent raise 'should be save first' if self.new_record? raise 'should be same class' if self.class != parent.class raise 'should not be self' if self.id == parent.id raise 'should not inherit descents' if self.descent_ids.include? parent.id raise 'should not inherit parent' if self.parent.try(:id) == parent.id self.class.transaction do inherit_node.destroy create_inherit_node(:parent_id=>parent.inherit_node.id) end end
inherit_association(name, options={:include=>false})
click to toggle source
# File lib/customize/inherited.rb, line 94 def inherit_association name, options={:include=>false} a = association(name) sql = ascents(options).joins(name).select("#{a.aliased_table_name}.#{a.klass.primary_key}").to_sql a.klass.from("(#{sql}) as subquery, #{a.klass.table_name}"). where("#{a.klass.table_name}.#{a.klass.primary_key} = subquery.#{a.klass.primary_key}") end
label()
click to toggle source
# File lib/customize/inherited.rb, line 73 def label self.to_s end
parent()
click to toggle source
# File lib/customize/inherited.rb, line 65 def parent inherit_node.parent_node.try(:node) end