如何在继承的类上形成多态has_many

时间:2016-04-30 06:18:33

标签: ruby-on-rails inheritance sti

在Rails 4.2应用程序中,我有一个继承自Draftsman的模型。

module ActsAs
  module Votable
    extend ActiveSupport::Concern
    included do
      has_many :votes_for, 
        class_name: 'ActsAs::Vote',
        as: :votable, 
        dependent: :destroy
    end
  end
end

用户可以投票批准/拒绝编辑,ActsAs :: Votable mixin添加了这种多态关联和方法。

ActsAs::Vote.last
=> #<ActsAs::Vote id: 10, votable_id: 6, votable_type: "Draftsman::Draft">

这适用于大多数父模型,但我在使用这个继承的Draftsman类时遇到了麻烦。

我可以创建投票

@draft = ActsAs::Draft.find(6)
@draft.votes_for
=> #<ActiveRecord::Associations::CollectionProxy []>

但我无法退回选票

ActsAs::Vote.last
=> #<ActsAs::Vote id: 10, votable_id: 6, votable_type: "ActsAs::Draft">
@draft = ActsAs::Draft.find(6)
@draft.votes_for
=> #<ActiveRecord::Associations::CollectionProxy []>

我尝试修改投票创建方法,将votable_type设置为ActsAs :: Draft而不是继承的Draftsman :: Draft,但同样的问题仍然存在。

@draft = Draftsman::Draft.find(6)
@draft.votes_for
NoMethodError: undefined method `votes_for' for #<Draftsman::Draft:0x007fd7e6de9660>

这种关系显然没有在Draftsmans :: Draft

上定义
@draft

ActsAs::Vote.all显示表中存在记录时,为什么我无法通过swap()获取子投票?

1 个答案:

答案 0 :(得分:1)

使用与STI的多态关联时,这是一个已知问题。

请参阅:Why polymorphic association doesn't work for STI if type column of the polymorphic association doesn't point to the base model of STI?

就我个人而言,我自己使用store_base_sti_class(gem:https://github.com/appfolio/store_base_sti_class)来解决这个问题,它使用Rails修补STI行为。