在has_many :through关系中指定外键

6
我有以下三个模型:用户,项目和任务分配。
一个用户通过任务分配与多个项目有关联。然而,任务有两个外键与用户有关: user_id(表示被指派项目的用户)和completer_id(表示完成项目的用户)。
通常,user_id和completer_id将是相同的(如果被指派项目的用户完成它)。但是,如果另一个用户完成它,user_id和completer_id将不同。
在我的用户模型中,我有以下内容:
class User < ActiveRecord::Base
  has_many   :assignments
  has_many   :incomplete_assignments, :class_name => 'Assignment',
    :conditions  => 'completer_id IS NULL'
  has_many   :completed_assignments, :class_name => 'Assignment',
    :foreign_key => 'completer_id'

  # this is the important one
  has_many   :incomplete_projects,
    :through     => :assignments,
    :source      => :project,
    :conditions  => 'completer_id IS NULL'
end

我想创建另一个关联,名为:completed_projects,该关联使用completer_id作为:through模型中用户的外键,而不是:user_id。这样做是否可行?
此外,我知道:foreign_key选项,但在使用:through时会被忽略,因此我想知道是否有一种方法可以在没有它的情况下进行操作。
最后,我应该提到,如果无法以这种方式完成并且有人能想到更好的方法,我也可以接受其他设计。

5
欢迎尝试使用ActiveRecord进行一些中等复杂度的操作。 :) - hobodave
2个回答

3

如果ActiveRecord无法轻松地表达关系,则您始终可以使用SQL进行选择:

has_many :completed_projects,
:class_name => "Project",
:finder_sql => 'SELECT p.* FROM projects p ' +
  'INNER JOIN assignments a ON p.id=a.project_id ' +
  'INNER JOIN users u on u.id=a.completer_id ' +
  'WHERE u.id=#{id}'

据我所知,这是唯一的方法。谢谢你这么做。 - jakeboxer
不幸的是,使用:finder_sql会破坏链接。user.completed_projects.limit(2)将无法工作。 - Joe Van Dyk

2

你的作业表中是否还有其他元数据?如果没有,我建议使用habtm,并将completer_id添加到projects表中,这样做更加合理。

如果你需要或者想要使用has_many :through,你可以考虑使用named_scopes(如果Rails版本允许),这样你就可以使用user.projects.completeduser.projects.incomplete来查询了。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接