2009-06-14 67 views
7

即時通訊DataMapper ORM初學者,所以我有關於複雜查詢的問題。複雜DataMapper查詢關聯

首先,這裏被簡化數據對象:

​​

這是DB數據看起來的樣子:

+ ------- + + ------- + + ------- + 
| Users | | Items | | Actions | 
+ ------- + + ------- + + ------- + 
| 1 | u1 | | 3 | i1 | | 1 | 4 | 
| 2 | u2 | | 4 | i2 | | 1 | 3 | 
| ....... | | 5 | i3 | | 1 | 4 | 
+ ------- + | ....... | | 1 | 5 | 
      + ------- + | 1 | 6 | 
         | 1 | 3 | 
         | ....... | 
         + ------- + 

因此,例如用戶1已經觀看過的一些項目N次。而我無法弄清楚,如何選擇與用戶相關的項目和他們的行動量。

例如,對於用戶1的結果應該是這樣的:

+ -------------------- | 
| Items (item_id, num) | 
+ -------------------- | 
| 3, 2     | 
| 4, 2     | 
| 5, 1     | 
| 6, 1     | 
+ -------------------- + 

P.S.常規的SQL查詢符合我的需求:

SELECT i.id, i.title, COUNT(*) as 'num' 
FROM actions a 
JOIN items i on i.id = a.item_id 
WHERE a.user_id = {USERID} 
GROUP by a.id 
ORDER BY num DESC 
LIMIT 10; 

那麼,如何才能做到這一點,是有關於複雜的DataMapper查詢的任何文檔?

回答

2

據我所知,datamapper或其插件中沒有運算符組。如果有的話,它會隨着彙總函數(count,min,max,avg)一起進入dm-aggregates。這使得在不使用sql的情況下很難在一個查詢中複製你想要的內容。

你可以嘗試這樣的事:

require 'dm-aggregates' 

Item.all.map do |item| 
    [item.title,item.actions.count(:user_id=>@user_id)] 
end 

但是,你可以很容易地把你的SQL,並在FN包裹。

class User 
    def item_views 
    repository.adapter.query "SELECT i.id, i.title, COUNT(*) as 'num' 
    FROM actions a 
    JOIN items i on i.id = a.item_id 
    WHERE a.user_id = {USERID} 
    GROUP by a.id 
    ORDER BY num DESC 
    LIMIT 10;" 
    end 
end 

repository.adapter.query返回結構的數組,所以你可以不喜歡

user.item_views[0].title 
12

事情,免得有人還在納悶:

Action.aggregate(:item_id, :all.count, :user_id => 1, :order => [item_id.asc]) 

將返回類似

[ [ 3, 2 ], 
    [ 4, 2 ], 
    [ 5, 1 ], 
    [ 6, 1 ] 
] 

沒有辦法在這裏命令all.count,但它會得到你想要的數據:)

+0

感謝 - 它從DataMapper文檔中並不完全清楚。 DM比AR產生更嚴格的SQL代碼,但需要像這樣的StackOverflow答案來學習如何。 – 2013-03-11 16:49:51