class Avo::Fields::BelongsToField
def can_create?(final_target_resource = target_resource)
- `can_create: true` option is present
Only can create when:
field :user, as: :belongs_to, can_create: true
def can_create?(final_target_resource = target_resource) @can_create && final_target_resource.authorization.authorize_action(:create, raise_exception: false) end
def database_id
def database_id # If the field is a polymorphic value, return the polymorphic_type as key and pre-fill the _id in fill_field. return :"#{polymorphic_as}_type" if polymorphic_as.present? foreign_key rescue id end
def database_value
def database_value target_resource.id rescue nil end
def default_name
def default_name return polymorphic_as.to_s.humanize if polymorphic_as.present? super end
def field_label
def field_label label end
def field_value
def field_value value.send(database_value) rescue nil end
def fill_field(record, key, value, params)
def fill_field(record, key, value, params) return record unless record.methods.include? key.to_sym if polymorphic_as.present? valid_model_class = valid_polymorphic_class params[:"#{polymorphic_as}_type"] record.send(:"#{polymorphic_as}_type=", valid_model_class) # If the type is blank, reset the id too. id_from_param = params["#{polymorphic_as}_id"] if valid_model_class.blank? || id_from_param.blank? record.send(:"#{polymorphic_as}_id=", nil) else record_id = target_resource(record:, polymorphic_model_class: value.safe_constantize).find_record(id_from_param).id record.send(:"#{polymorphic_as}_id=", record_id) end else record_id = value.blank? ? value : target_resource(record:).find_record(value).id record.send(:"#{key}=", record_id) end record end
def foreign_key
def foreign_key @foreign_key ||= if polymorphic_as.present? polymorphic_as elsif @record.present? get_model_class(@record).reflections[@relation_method].foreign_key elsif @resource.present? && @resource.model_class.reflections[@relation_method].present? @resource.model_class.reflections[@relation_method].foreign_key end end
def form_field_label
def form_field_label "#{id}_id" end
def get_model_class(record)
def get_model_class(record) if record.nil? @resource.model_class elsif record.instance_of?(Class) record else record.class end end
def get_record
def get_record @record || @resource.record end
def id_input_foreign_key
def id_input_foreign_key if is_polymorphic? "#{foreign_key}_id" else foreign_key end end
def index_link_to_record
def index_link_to_record if @link_to_record.present? get_record else value end end
def index_link_to_resource
def index_link_to_resource if @link_to_record.present? @resource else target_resource end end
def initialize(id, **args, &block)
def initialize(id, **args, &block) args[:placeholder] ||= I18n.t("avo.choose_an_option") super(id, **args, &block) @searchable = args[:searchable] == true @polymorphic_as = args[:polymorphic_as] @types = args[:types] @relation_method = id.to_s.parameterize.underscore @allow_via_detaching = args[:allow_via_detaching] == true @attach_scope = args[:attach_scope] @polymorphic_help = args[:polymorphic_help] @target = args[:target] @use_resource = args[:use_resource] || nil @can_create = args[:can_create].nil? ? true : args[:can_create] @link_to_record = args[:link_to_record].present? ? args[:link_to_record] : false @link_to_child_resource = args[:link_to_child_resource] end
def is_polymorphic?
def is_polymorphic? polymorphic_as.present? rescue false end
def label
def label return if target_resource.blank? target_resource.new(record: value)&.record_title end
def options
def options values_for_type end
def polymorphic_form_field_label
def polymorphic_form_field_label "#{id}_type" end
def reflection
def reflection reflection_for_key(id) rescue nil end
def reflection_for_key(key)
def reflection_for_key(key) get_model_class(get_record).reflections[key.to_s] rescue nil end
def relation_model_class
def relation_model_class @resource.model_class end
def target_resource(record: @record, polymorphic_model_class: value&.class)
def target_resource(record: @record, polymorphic_model_class: value&.class) @target_resource ||= if use_resource.present? use_resource elsif is_polymorphic? if polymorphic_model_class.present? get_resource_by_model_class(polymorphic_model_class) else return nil end else reflection_key = polymorphic_as || id reflection_object = record.class.reflect_on_association(reflection_key) if (link_to_child_resource || @resource&.link_to_child_resource) && value.present? get_resource_by_model_class(value.class.to_s) elsif reflection_object.klass.present? get_resource_by_model_class(reflection_object.klass.to_s) elsif reflection_object.options[:class_name].present? get_resource_by_model_class(reflection_object.options[:class_name]) else App.get_resource_by_name reflection_key end end end
def to_permitted_param
def to_permitted_param if polymorphic_as.present? return [:"#{polymorphic_as}_type", :"#{polymorphic_as}_id"] end foreign_key.to_sym end
def type_input_foreign_key
def type_input_foreign_key if is_polymorphic? "#{foreign_key}_type" end end
def valid_polymorphic_class(possible_class)
def valid_polymorphic_class(possible_class) types.find do |type| type.to_s == possible_class.to_s end end
def value
def value if is_polymorphic? # Get the value from the pre-filled association record super(polymorphic_as) else # Get the value from the pre-filled association record super(@relation_method) end end
def values_for_type(model = nil)
def values_for_type(model = nil) resource = target_resource resource = Avo.resource_manager.get_resource_by_model_class model if model.present? query = resource.query_scope if attach_scope.present? query = Avo::ExecutionContext.new(target: attach_scope, query: query, parent: get_record).handle end query.all.limit(Avo.configuration.associations_lookup_list_limit).map do |record| [resource.new(record: record).record_title, record.to_param] end.tap do |options| options << t("avo.more_records_available") if options.size == Avo.configuration.associations_lookup_list_limit end end