# File lib/no_brainer/document/association/belongs_to.rb, line 23 def primary_key # We default the primary_key to `:id' and not `target_model.pk_name', # because we don't want to require the target_model to be already loaded. # (We want the ability to load models in any order). # Using target_model.pk_name and allowing lazy loading of models is # difficult due to the inexistant API to remove validations if the # foreign_key name was to be changed as the pk_name gets renamed. return options[:primary_key].to_sym if options[:primary_key] NoBrainer::Document::PrimaryKey::DEFAULT_PK_NAME.tap do |default_pk_name| # We'll try to give a warning when we see a different target pk name (best effort). real_pk_name = target_model.pk_name rescue nil if real_pk_name && real_pk_name != default_pk_name raise "Please specify the primary_key name on the following belongs_to association as such:\n" + " belongs_to :#{target_name}, :primary_key => :#{real_pk_name}" end end end
class NoBrainer::Document::Association::BelongsTo::Metadata
Constants
- VALID_OPTIONS
Public Instance Methods
base_criteria(target_class = nil)
click to toggle source
# File lib/no_brainer/document/association/belongs_to.rb, line 54 def base_criteria(target_class = nil) model = target_model(target_class) model ? model.without_ordering : nil end
cast_attr(key, value, target_class = nil)
click to toggle source
# File lib/no_brainer/document/association/belongs_to.rb, line 109 def cast_attr(key, value, target_class = nil) case value when target_model(target_class) [foreign_key, value.__send__(primary_key)] when nil if options[:polymorphic] [[foreign_type, foreign_key], nil] else [foreign_key, nil] end else raise NoBrainer::Error::InvalidType.new( model: owner_model, attr_name: key, type: target_model, value: value ) end end
eager_load_owner_key()
click to toggle source
# File lib/no_brainer/document/association/belongs_to.rb, line 126 def eager_load_owner_key; foreign_key; end
eager_load_owner_type()
click to toggle source
# File lib/no_brainer/document/association/belongs_to.rb, line 127 def eager_load_owner_type; foreign_type; end
eager_load_target_key()
click to toggle source
# File lib/no_brainer/document/association/belongs_to.rb, line 128 def eager_load_target_key; primary_key; end
foreign_key()
click to toggle source
# File lib/no_brainer/document/association/belongs_to.rb, line 13 def foreign_key options[:foreign_key].try(:to_sym) || :"#{target_name}_#{primary_key}" end
foreign_type()
click to toggle source
# File lib/no_brainer/document/association/belongs_to.rb, line 17 def foreign_type return nil unless options[:polymorphic] options[:foreign_type].try(:to_sym) || (:"#{target_name}_type") end
hook()
click to toggle source
Calls superclass method
NoBrainer::Document::Association::Core::Metadata#hook
# File lib/no_brainer/document/association/belongs_to.rb, line 60 def hook super # TODO set the type of the foreign key to be the same as the target's primary key if owner_model.association_metadata.values.any? { |assoc| assoc.is_a?(self.class) && assoc != self && assoc.foreign_key == foreign_key } raise "Cannot declare `#{target_name}' in #{owner_model}: the foreign_key `#{foreign_key}' is already used" end if options[:polymorphic] && options[:class_name] raise 'You cannot set class_name on a polymorphic belongs_to' end if options[:polymorphic] if options[:uniq] || options[:unique] owner_model.field(foreign_type, uniq: { scope: foreign_key }) owner_model.index([foreign_type, foreign_key]) else owner_model.field(foreign_type) end end owner_model.field(foreign_key, store_as: options[:foreign_key_store_as], index: options[:index]) unless options[:validates] == false owner_model.validates(target_name, options[:validates]) if options[:validates] uniq = options[:uniq] || options[:unique] if uniq owner_model.validates(foreign_key, :uniqueness => uniq) end if options[:required] owner_model.validates(target_name, :presence => options[:required]) else # Always validate the foreign_key if not nil. owner_model.validates_each(foreign_key) do |doc, attr, value| if !value.nil? && value != doc.pk_value && doc.read_attribute_for_validation(target_name).nil? doc.errors.add(attr, :invalid_foreign_key, :target_model => target_model, :primary_key => primary_key) end end end end delegate("#{foreign_key}=", :assign_foreign_key, :call_super => true) delegate("#{target_name}_changed?", "#{foreign_key}_changed?", :to => :self) add_callback_for(:after_validation) end
primary_key()
click to toggle source
target_model(target_class = nil)
click to toggle source
# File lib/no_brainer/document/association/belongs_to.rb, line 42 def target_model(target_class = nil) return if options[:polymorphic] && target_class.nil? model_name = if options[:polymorphic] target_class else options[:class_name] || target_name.to_s.camelize end get_model_by_name(model_name) end