没有外键的ActiveRecord关联

Fai*_*sal 3 activerecord ruby-on-rails associations

我正在尝试在用户之间建立关系模型.用户可以发起关系,也可以从其他用户接收关系.因此,db中的关系表具有外键"initiator_id"和"recipient_id".
现在,我可以使用以下关联来计算用户发起或接收的关系:

has_many :initiated_relations, :foreign_key => :initiator_id, :class_name => 'Relation', :dependent => :destroy
has_many :received_relations,  :foreign_key => :recipient_id, :class_name => 'Relation', :dependent => :destroy
Run Code Online (Sandbox Code Playgroud)

我想要做的是建立一个关联,它将获取属于用户(发起或接收)的所有关系.尝试以下操作无效,并抱怨缺少"user_id"字段:

has_many :relations, :conditions => 'recipient_id = #{id} or initiator_id = #{id}'
Run Code Online (Sandbox Code Playgroud)

如何创建仅基于条件字段的关联,而不查找默认的foreign_key?或者可能有一种完全不同的方法来解决这个问题?

Mat*_*att 8

从你的评论到@ neutrino的答案我明白,你只需要这种"关系"来进行只读操作.如果您使用的是Rails 3,则可以利用它使用延迟提取的事实.该where()方法返回ActiveRecord::Relation对象,稍后您可以修改该对象.所以你可以定义一个像这样的方法:

def User < ActiveRecord::Base
  def all_relations
    Relation.where("initiator_id => ? OR recipient_id = ?", id, id)
  end
end
Run Code Online (Sandbox Code Playgroud)

然后你可以这样做:

User.all_relations.where(:confirmed => true).all
Run Code Online (Sandbox Code Playgroud)


ale*_*dev 5

好吧,我可以考虑使用finder_sql它:

has_many :relations, :finder_sql => 'select * from relations right outer join users
    on relations.recipient_id = #{id} or relations.initiator_id = #{id}'
Run Code Online (Sandbox Code Playgroud)

除此之外,你可以编写一个返回两个关系关联的联合数组的方法,但是你将失去关联接口(phew)的优势.

也许有人会提出更好的解决方案.