Rails嵌套与first_or_create的关联

时间:2013-04-11 05:19:07

标签: ruby-on-rails associations has-many-through has-many

我有一个comic_books表,其中有许多问题,每个问题都有一个author and illustrator,目前只存储为字符串。使用has_many:through漫画书来发布作品很棒,现在我正试图找出如何为作者和插图画家添加关联。

问题在于作者和插画家有时是同一个人。如果你点击插图画家,我想看看他/她写的或插图的具体问题。如果我设置has_one belongs_to association,我只会获得插图或作者的卷结果,但我想要同一个“创建者”。

因此,我引导我尝试creator表,但我无法弄清楚如何放置关联。我想要一个创作者表来存储name,并在作家和插图画家中存储creator_id

然后我想致电

issue.illustrator.first_or_create!('bob smith')

但那不对。 我不想要独立的插图画家和作家表,因为他们每个都有相同的名字。我需要进一步抽象出来,但我似乎无法弄明白。

我想我想创建一个新的创建者记录,如果一个不存在并将creator_id存储到illustrator表中,以便我可以引用issue.illustrator.name,但名称值实际上在创建者表中...

是否有更好的方法来完成整个任务?

1 个答案:

答案 0 :(得分:0)

关于你试图指派一名插画家的问题,你可能想要这样做:

issue.illustrator = Illustrator.first_or_create(name: "Bob Smith")

取决于您使用的型号。我对你拥有的模型以及如何在那里构建他们的关联有点失落。

我可能处理这种情况的方法是为作者和插图画家使用Creator类,并使用第三个交叉引用模型(例如,调用Involvement)将其链接到特定的Issues,并指定他们在第三个模型中的角色。关联看起来像这样(忽略Comic,因为它听起来像是Issue跟踪作者/插图画家):

class Issue < ActiveRecord::Base
  has_many :involvements
  has_many :creators, through: :involvements
  ...
end

class Creator < ActiveRecord::Base
  has_many :involvements
  has_many :issues, through: :involvements
  ...
end

class Involvement < ActiveRecord::Base
  belongs_to :issue
  belongs_to :creator

  # This model would then have an extra property to store the type of involvement
  # ie. author, illustrator, author/illustrator
  attr_accessible :type, ...
end

(我倾向于使type上的Involvement属性为比特屏蔽整数,因此作者可能是1,插图画家可能是2,作者/插画家3。)

这样,您可以使用以下内容向Creator添加Issue

inv = Issue.involvements.create(type: ...) # Whatever's appropriate
inv.creator = Creator.find_or_create('Bob Smith')