2013-12-12 25 views
0

的價值觀我有3種型號:軌道4:LEFT JOIN越來越加盟模式

class User < ActiveRecord::Base 
    has_many :likes, :dependent => :destroy 
end 

class Movie < ActiveRecord::Base 
    has_many :likes, :primary_key => :mid, :foreign_key => :item_id 
end 

class Like < ActiveRecord::Base 
    belongs_to :user 
    belongs_to :movie, :foreign_key => :item_id, :primary_key => :mid 
end 

除了喜歡一部電影,用戶可以通過像模式改變喜歡電影的一些風格選項,如展開 & pin

# likes 
+---------------------------------------+ 
| user_id | item_id | expanded | pinned | 
|---------|---------|----------|--------| 
| 1 | 1 | true | true | 
| 1 | 2 | false | true | 
+---------------------------------------+ 

# movies 
+-----------------------+ 
| title | mid | year | 
|----------|-----|------| 
| Avatar | 1 | 2009 | 
| Gladiator| 2 | 2000 | 
| Shrek | 3 | 2001 | 
+-----------------------+ 

在這個例子中,用戶喜歡的電影阿凡達&角鬥士,而改變了電影的狀態(expandedpinned)。

現在,當我想在視圖中顯示所有3部電影時,我想按照登錄用戶的意圖顯示電影的狀態。 (Avatar => expanded & pinned, Gladiator => pinned, Shrek => nothing)

我到目前爲止的解決方案是加載全部電影,然後檢查查詢每部電影的狀態......這導致了太多的查詢。

所需的表是這樣的:

+---------------------------------------------------------------+ 
| user_id | expanded | pinned | item_id/mid | title | year | 
|---------|----------|--------|---------------|----------|------| 
| 1 | true | true |  1  | Avatar | 2006 | 
| 1 | false | true |  2  | Gladiator| 2000 | 
| null | null | null |  3  | Shrek | 2001 | 
+---------------------------------------------------------------+ 

據我瞭解,查詢,應建立通過includes聯接。

               # (1) 
movies = Movie.includes(:likes).where(:likes => {:user_id => current_user.id }).references(:likes) 

但通過電影循環的時候,我似乎無法獲得加入likes表的數據,如expanded狀態:

movies.each do |m| 
    puts m.expanded 
    puts m.likes.expanded 
end 
# => undefined method `expanded' for #ActiveRecord::Associations::CollectionProxy::ActiveRecord_Associations_CollectionProxy_Like:0x007fae7ea51f48 

我似乎無法弄清楚出了什麼問題。提前致謝!

回答

3

我認爲Rails是不給解釋的異常很不錯,但你應該嘗試瞭解他們從來沒有少:

# => undefined method `expanded' for #ActiveRecord::Associations::CollectionProxy::ActiveRecord_Associations_CollectionProxy_Like:0x007fae7ea51f48 

所以,這個錯誤會告訴你,有沒有一種方法expanded,你覺得它應該。

Nr。這種事情的1個原因是你自己代碼中的錯誤!

一個好的程序員總是想着什麼,他或她可能做錯了,讓我們看看你的代碼:

m.likes.expanded 

在這裏,我們有Movie類的對象。從您提供的代碼中,我們可以看到它has_many喜歡。這就是爲什麼最後有s。這不是like而是likes。所以它是一個對象列表。在這種情況下,它是從數據庫加入的延遲加載的對象數組。在Rails中,這些由ActiveRecord::Associations::CollectionProxy處理。

因此,您在該代理對象的實例上調用expanded,但是您想調用它的實例爲Like

如果你想這樣做,你需要迭代這些,或選擇一個相關的,可能就像當前用戶所做的那樣。

+0

你是我的英雄!我的db結構意味着'm.likes'總是包含1個項目,但是盲目地假設Rails會自動選擇生成的列表的第一個是我出錯的地方。 因此,使用'm.likes.first.expanded'就像一個魅力! :) –

+0

在這種情況下,你應該使用'has_one'關係 – phoet

+0

我進一步測試後認識到,有許多喜歡屬於電影,而不僅僅是一個。所以我最終使用: 'movies = Movie.includes(:likes).references(:likes)'。後來在循環中,我打電話:'like = movie.likes.where(:likes => {:user_id => current_user.id})' 您的回答幫助我達到了那裏:) –