为啥我的多态类型是我的模型继承的类?

Posted

技术标签:

【中文标题】为啥我的多态类型是我的模型继承的类?【英文标题】:Why is my polymorphic type the class that my model inherits from?为什么我的多态类型是我的模型继承的类? 【发布时间】:2018-11-21 03:21:09 【问题描述】:

我有一个继承自其他基础模型的模型:

class Instructor < User

我有另一个具有多态关联的模型:

class SiteResource < ApplicationRecord
  belongs_to :site
  belongs_to :resource,  polymorphic: true
end

但是当我创建新对象时,它的资源类型是用户,而不是教师

irb(main):005:0> SiteResource.create(site: Site.first, resource: Instructor.first)
+----+---------+-------------+---------------+--------+-------------------------+-------------------------+
| id | site_id | resource_id | resource_type | status | created_at              | updated_at              |
+----+---------+-------------+---------------+--------+-------------------------+-------------------------+
| 2  | 1       | 21          | User          | 1      | 2018-06-11 19:47:29 UTC | 2018-06-11 19:47:29 UTC |
+----+---------+-------------+---------------+--------+-------------------------+-------------------------+

这是:

    有意? 有用吗? 坏消息? 可配置?

【问题讨论】:

嗯,我猜从 ActiveRecord 模型继承的模型本身并不是 Activerecord 模型(嗯..)。这里有一个关于它是如何存储的解释api.rubyonrails.org/classes/ActiveRecord/Inheritance.html我从来没有使用过这样的设计,你对这种继承模型的目标是什么? 【参考方案1】:

直接来自文档的示例,粘贴文字副本,因为我无法像他们那样更好地解释它

class Asset < ActiveRecord::Base
  belongs_to :attachable, polymorphic: true
end

class Post < ActiveRecord::Base
  has_many :assets, as: :attachable         # The :as option specifies the polymorphic interface to use.
end

@asset.attachable = @post

将多态关联与单表继承 (STI) 结合使用有点棘手。为了使关联按预期工作,请确保将 STI 模型的基本模型存储在多态关联的类型列中。继续上面的资产示例,假设有使用 STI 的帖子表的访客帖子和成员帖子。在这种情况下,posts表中必须有一个类型列

注意:在分配可附加对象时会调用 attachable_type= 方法。 附件的类名作为字符串传递

class Asset < ActiveRecord::Base
  belongs_to :attachable, polymorphic: true

  def attachable_type=(class_name)
     super(class_name.constantize.base_class.to_s)
  end
end

class Post < ActiveRecord::Base
  # because we store "Post" in attachable_type now dependent: :destroy will work
  has_many :assets, as: :attachable, dependent: :destroy
end

class GuestPost < Post
end

class MemberPost < Post
end

您需要的官方文档:http://api.rubyonrails.org/classes/ActiveRecord/Associations/ClassMethods.html#label-Polymorphic+Associations

【讨论】:

以上是关于为啥我的多态类型是我的模型继承的类?的主要内容,如果未能解决你的问题,请参考以下文章

继承和已知类型问题

XML 序列化和继承类型

为啥我的类不继承父类?

多态及鸭子类型

为啥我的类不继承其基类中定义的方法?

第二十五天