【问题标题】:How to find or update a record though a nested attributes form (Rails 6)如何通过嵌套属性表单查找或更新记录(Rails 6)
【发布时间】:2021-01-27 21:40:48
【问题描述】:

tldr:如何查找和更新通过嵌套关联创建记录?

我有一个属于 Lead 模型的 Registrations 模型。当用户提交注册表单时,潜在客户是通过嵌套属性创建的。这工作正常,但现在我需要更新注册,以便它创建新的潜在客户,或者如果该电子邮件已存在潜在客户,则查找并更新潜在客户。

registration.rb:

class Registration < ApplicationRecord
  belongs_to :showing
  belongs_to :lead

  accepts_nested_attributes_for :lead
  validates_associated :lead

end

lead.rb

class Lead < ApplicationRecord
  belongs_to :account
  has_many :registrations, dependent: :destroy
  has_many :showings, through: :registrations
  validates :name, :email, :phone, presence: true

end

registrations_controller.rb

class RegistrationsController < ApplicationController
  before_action :set_account

  def index
    redirect_to new_showing_registration_path
  end

  def new
    @registration = @showing.registrations.build
    @lead = Lead.new
  end

  def create
    @showing = Showing.find(params[:showing_id])
    @registration = @showing.registrations.build(registration_params)
    if @registration.save
      redirect_to new_showing_registration_path, notice: 'Thank you for registering.'
    else
      render :new, status: :unprocessable_entity
    end
  end

  def show
    redirect_to new_showing_registration_path
  end

  def edit
    @showing = Showing.find(params[:showing_id])
    @registration = Registration.find(params[:id])
    @account_id = @showing.listing.account.id.to_i
  end

  def update
    @registration = Registration.find(params[:id])
    if @registration.update(registration_params)
      redirect_to new_showing_registration_path, notice: 'Thank you for registering.'
    else
      render :edit, status: :unprocessable_entity
    end
  end

  private
    def registration_params
      params.require(:registration).permit(lead_attributes: [:account_id, :id, :name, :email, :phone, :agent, :mortgage, :source])
    end

    def set_account
      @showing = Showing.find(params[:showing_id])
      @account_id = @showing.listing.account.id.to_i
    end
end

【问题讨论】:

    标签: ruby-on-rails ruby ruby-on-rails-6


    【解决方案1】:

    也许这个会有所帮助

    https://stackoverflow.com/a/3580267/11544219

    或者这个

    https://dev.to/katkelly/why-yes-i-ll-accept-those-nested-attributes-18f7

    
    class Registration < ApplicationRecord
      belongs_to :showing
      belongs_to :lead
    
      accepts_nested_attributes_for :lead
      validates_associated :lead
    
      def autosave_associated_records_for_lead
       existed_lead = Lead.find_by(registration: self)
       if existed_lead.present?
         existed_lead.update!(lead.attributes)
       else
         lead.save!
       end
      end
    
    end
    

    【讨论】:

    • 谢谢!这很接近,但是当覆盖自动保存时,我开始遇到在父级上设置lead_id的问题。不完全确定为什么。因此,我决定使用您的类似逻辑进行回调。如果您有兴趣,我发布了我的解决方案。再次感谢!
    • 哦,回调也有效。确定伙计
    【解决方案2】:

    对于正在开发类似功能的其他人,这是我解决它的方法(下)。最终,我选择使用回调而不覆盖自动保存方法。覆盖自动保存方法时,我在连接表的父对象上设置嵌套对象 ID 时遇到问题。所以,我采用了以下回调过程:

    1. 检查该电子邮件是否存在潜在客户
    2. 如果存在,则使用新的潜在客户属性更新现有潜在客户
    3. 将新潜在客户设置为更新后的现有潜在客户
    4. 如果线索不存在,则将新线索传回控制器进行创建
    class Registration < ApplicationRecord
      belongs_to :showing
      belongs_to :lead
      accepts_nested_attributes_for :lead, :reject_if => :all_blank, allow_destroy: true
      before_validation :update_or_create_lead
    
      private
    
      def update_or_create_lead
        existing = Lead.find_by(email: self.lead.email)
        if existing
          existing.update(
            name: lead.name,
            phone: lead.phone,
            agent: lead.agent,
            mortgage: lead.mortgage,
            source: lead.source
        )
          self.lead = existing
        else
          self.lead
        end
      end
    
    end
    

    【讨论】:

      猜你喜欢
      • 2021-10-22
      • 2019-12-06
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-11-03
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多