has_one 的 CollectionProxy 方便吗?

Convenience of CollectionProxy for has_one?

我有一个 Accounts 模型,它有很多 CreditCards 和一个 BillingInfo

CreditCards 控制器中,我在 CollectionProxy:

的帮助下初始化
class CreditCardsController < ApplicationController
  def create
    credit_card = current_account.credit_cards.new(credit_card_params)

    ...
  end
end

但是,这不适用于 has_one 关联:

class BillingInfosController < ApplicationController
  def create
    billing_info = current_account.billing_info.new(billing_info_params)

    ...
  end
end

原因是;在 current_account 上调用 billing_info 执行 return nil 而不是空 CollectionProxy,这会导致在 nil 上发送 new 并与 NoMethodError.

有没有办法使用CollectionProxy或类似的东西继续使用

current_account.billing_info.new(billing_info_params)

而不是像

BillingInfo.new(billing_info_params.merge(account_id: current_account.id))

要初始化?提前致谢!

您应该可以使用 current_account.build_billing_infocurrent_account.create_billing_info,它们是 has_one 协会添加的方法。

When initializing a new has_one or belongs_to association you must use the build_ prefix to build the association, rather than the association.build method that would be used for has_many or has_and_belongs_to_many associations. To create one, use the create_ prefix.

有关这些方法和 Active Record 为您添加的其他方法的更多信息,请参阅 has_one association reference

一个解决方案是确保每个帐户 has_one billing_info 您可以使用 after_create 回调来创建帐户的 billing_info

另一个是先得到billing_info billing_info = current_account.billing_info || current_account.build_billing_info billing_info.assign_attributes(billing_info_params)