Ruby on rails 可以将查找多态性的范围转换为两个模型之间的关联吗?
假设Ruby on rails 可以将查找多态性的范围转换为两个模型之间的关联吗?,ruby-on-rails,associations,rails-activerecord,Ruby On Rails,Associations,Rails Activerecord,假设发票属于可开票,一种多态类型,可能是可开票订阅,订阅卡和购买 Invoice表包含列invoiceable\u type和invoiceable\u id。例如,如果我想通过多态性检索与SubscriptionCart相关的所有Invoice,我可以执行Invoice.where(invoiceable\u type:“SubscriptionCart”) 现在,我如何通过多态性将这样的范围转换为Invoice和SubscriptionCart之间的直接关联 我已尝试将所属\u to:订阅车
发票属于可开票
,一种多态类型,可能是可开票
订阅
,订阅卡
和购买
Invoice
表包含列invoiceable\u type
和invoiceable\u id
。例如,如果我想通过多态性检索与SubscriptionCart
相关的所有Invoice
,我可以执行Invoice.where(invoiceable\u type:“SubscriptionCart”)
现在,我如何通过多态性将这样的范围转换为Invoice
和SubscriptionCart
之间的直接关联
我已尝试将所属\u to:订阅车
添加到发票
模型,结果是@Invoice.subscription\u车
返回nil
这是有意义的,因为表invoices
没有列subscription\u cart\u id
(也不应该,因为这就是我们使用多态性的原因)
但是我如何指定在可开票
中查找什么呢?
我尝试了class\u name::SubscriptionCart
和外键:subscription\u cart\u id
,但它仍然返回nil
精简模型:
发票型号:
首先,这看起来好多了。也就是说,由于多形性,并非所有发票都属于SubscriptionCart
。您可以通过def subscription\u cart将“关联”添加到实例中;可开票的_类型==“SubscriptionCart”?可开票:无;结束
否则从作用域的角度来看,您可以使用作用域:订阅车,->{SubscriptionCart.where(id:self.where(invoiceable\u type:“SubscriptionCart”)。选择(:invoiceable\u id))
这将返回所有“invoiceable”SubscriptionCart
对象。谢谢@engineersmnky。是否可以将其定义为关联,而不是作用域或类方法?类似于的内容属于:subscription\u cart
并可能引用变形的可开票类型
?很抱歉,我是Rails的新手,现在很难受理解多态性。
class Invoice < ApplicationRecord
belongs_to :invoiceable, polymorphic: true
scope :subscription_cart, -> {
where(invoiceable_type: "SubscriptionCart")
}
end
class SubscriptionCart < ApplicationRecord
include ::Invoiceable::Subscription
belongs_to :subscription
has_many :invoices, as: :invoiceable
end
class Subscription < ApplicationRecord
include ::Invoiceable::Subscription
belongs_to :user
has_many :subscription_carts, dependent: :restrict_with_exception
has_many :invoices, as: :invoiceable, dependent: :restrict_with_exception
end
module Invoiceable::Subscription
extend ActiveSupport::Concern
include Invoiceable
included do
def attributes_for_invoice_items
{}.tap do |attributes|
attributes["flat_fee"] = plan_invoice_item
attributes["delivery_price"] = delivery_price_item_invoice_item if plan.deliverable?
attributes["setup_fee"] = setup_invoice_item if setup_fee_billing_pending?
attributes["per_unit"] = per_unit_invoice_item if base_plan.per_unit?
end
end
end
end