【问题标题】:Polymorphic association with abstract class in rails与rails中抽象类的多态关联
【发布时间】:2019-03-09 20:40:08
【问题描述】:

所以这或多或少是我正在尝试的:

我为所有常见功能提取了一个抽象类,其中包括一个多态关联,所以它看起来像这样:

class Card < ActiveRecord::Base
  self.abstract_class = true
  belongs_to :cardable, polymorphic: true
  ...
end

class Spell < Card
  ...
end

class Unit < Card
  ...
end

现在,当我尝试对此使用多态关联时,如下所示:

  class Deck < ActiveRecord::Base
    has_many :cards, :as => :cardable
  end

  class Hand < ActiveRecord::Base
    has_many :cards, :as => :cardable
  end

belongs_to 部分工作正常, 即spell.cardable 按预期完美运行

但是,由于是抽象类,has_many 不能正常工作 即 hand.cardsdeck.cards 总是给出一个空的 ActiveRecord 关联

这是一个可行的模型,或者如果不是,那么对整个场景建模的更好方法是什么?

【问题讨论】:

  • 你为什么认为你应该首先在这里使用抽象类?没有更多信息,很难知道为什么或您在这里尝试做什么,因此无法提供答案。在 Rails 中使用模型并不是最佳实践。看这篇文章medium.com/@jeremy_96642/…
  • 我不知道 Ruby 中“抽象类”的概念。你能定义一下这个词吗?
  • @lacostenycoder 这是因为两个子类的行为非常相似;但是他们在架构上的差异迫使我不使用 STI
  • @CarySwoveland 抽象类是 rails 中的一个概念,其中:如果将类标记为抽象类,则它不需要相应的表(在较新的 rails 版本中,自动生成的 ApplicationRecord 类就是一个示例一样的)。然后您可以将其用作父类进行继承,其中每个子类将需要不同的表。
  • 乔希,感谢您的解释。

标签: ruby-on-rails ruby associations polymorphic-associations


【解决方案1】:

你可以通过使用初始化器来模拟一个抽象类

class Card < ActiveRecord::Base
  def initialize 
    raise "Card cannot be instantiated directly" if self.class == Card
  end
  belongs_to :cardable, polymorphic: true
  ...
end

您维护您的 STI 并拥有伪抽象类 请在stackoverflow上阅读comment

【讨论】:

  • 嗨,谢谢你的回答,但我在这种情况下根本没有性传播感染:)
  • 但是是的,如果它是 STI 会完美运行
【解决方案2】:

@JoshKurien 听起来您已经回答了自己的问题“它不需要相应的表”,但在您的情况下,cards 不是您数据库中的实际表吗?如果是这样,请摆脱这条线,因为它显然破坏了ActiveRecord 提供的多态性

self.abstract_class = true

也许更好的方法是让每个具有数据库表的模型类都定义为常规模型。如果您需要模型中的共享行为,您可以使用模型关注点并从共享关注点扩展这些模型吗?

How to use concerns in Rails 4

但有些人认为关注点是一个糟糕的设计,在这种情况下,您可能还想查看https://github.com/AndyObtiva/super_module 作为另一种选择。

【讨论】:

  • 不,卡片对我来说不是一张桌子。在这种情况下,有 4 个不同的表:spellsunitsdeckshands 抽象类用例非常真实。我知道这是破坏多态性。我想我的问题更多是关于什么是模拟这种情况的更好方法
  • @JoshKurien 我已经用其他一些想法更新了我的答案。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2020-08-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-01-05
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多