1

在我的Rails應用程序中,我有兩個模型: PersonCompany。我需要指定這些對象的任何對之間的多對多關係。所以,我應該可以這樣做:雙多態協會

@connections = @person.connections 

其中@connectionsPersonCompany對象的數組。

現在我已經創建ConnectionBinding模型,這和它不起作用通緝:

class ConnectionBinding < ActiveRecord::Base 
    belongs_to :connect_from, polymorphic: true 
    belongs_to :connect_to, polymorphic: true 
end 

它thougths ActiveRecord::HasManyThroughAssociationPolymorphicSourceError例外

有誰已經解決這個問題?任何建議感激。

回答

1

Thanx克里斯爲顯示這個想法。但我需要做一些改變才能完成這項工作。 克里斯例子的問題是,如果我打電話給person_connections方法它會產生錯誤的查詢。

Person.find(720).person_connections 

生成此SQL

SELECT "people".* FROM "people" 
INNER JOIN "connection_bindings" 
    ON "people"."id" = "connection_bindings"."connect_to_id" 
WHERE "connection_bindings"."person_id" = 720 
    AND "connection_bindings"."connect_to_type" = 'Person' 

person_id列應該是connect_from_id。所以我需要添加:as => :connect_from選項到has_many :connection_bindings來顯示ActiveRecord它的一個多態關聯。

has_many :connection_bindings, :as => :connect_from 
has_many :person_connections, :through => :connection_bindings, 
    :source => :connect_to, source_type: 'Person' 
has_many :company_connections, :through => :connection_bindings, 
    :source => :connect_to, source_type: 'Company' 

但它仍然不夠。我需要能夠獲得反向​​連接。所以如果Person @a增加連接到Person @b?方法連接應顯示在兩個方向@a.connections@b.connections之間的連接。

現在我想我可以通過添加幾個附加的關聯和聚合方法來做到這一點。

5

你需要告訴ActiveRecord它正在尋找的相關列。我猜你想有以下幾點:

class Person < ActiveRecord::Base 
    has_many :connection_bindings 
    has_many :companies, :through => :connection_bindings 
    has_many :people, :through => :connection_bindings 
end 

class company < ActiveRecord::Base 
    has_many :connection_bindings 
    has_many :companies, :through => :connection_bindings 
    has_many :people, :through => :connection_bindings 
end 

的問題有,你有兩個表將有ID的一列和Rails不知道看哪個表了。

例如,在數據庫中的任何給定connection_binding行上,connect_from可以是company_id或person_id,connect_to也是如此。所以你說:'嘿Rails,加載我關聯的ConnectionBindings',它會得到一行,connect_from是11,connect_to是12.但它做Person.find(12)或Company.find(12)?沒有辦法告訴!

相反,你得給Rails的一些信息:

class Person < ActiveRecord::Base 
    has_many :connection_bindings 
    has_many :person_connections, :through => :connection_bindings, :source => :to_connect, :source_type => 'Person' 
    has_many :company_connections, :through => :connection_bindings, :source => :to_connect, :source_type => 'Company 

    def connections 
    person_connections + company_connections 
    end 
end 

你需要建立一個在另一邊(以及相關的:from_connect的),但它取決於你如何'正在使用這些連接。應該足以讓你開始。

在Ruby和Rails的魔幻世界中,它的鍵入方式比您習慣的要多得多,但它卻是您嘗試構建的非常複雜的數據模式。這並不意味着它是不可能的 - Rails作爲一個好的框架不會阻止你做任何你真正想做的事情 - 但是爲了達到你的目的,需要一些明確性是不常見的。

+0

感謝名單指着我出去。你的回答非常有幫助。我在下一個答案中爲我寫下了實際的解決方案。 – RunFor 2013-03-13 01:04:57

0

關注:

module Linkable 
    extend ActiveSupport::Concern 

    included do 
    has_many :links_to, as: :linkable_to, class_name: 'Link' # [this]->[other object] 
    has_many :links_from, as: :linkable_from, class_name: 'Link' # [other object]->[this] 
    end 
end 

鏈接表:

class Link < ActiveRecord::Base 

    #The idea for this class is to by a double polymorphic table, linking an object to another object 
    belongs_to :linkable_from, :polymorphic => true 
    belongs_to :linkable_to, :polymorphic => true 
end