2012-08-15 54 views
4

我有用戶配置的列表,它可能(或可能不會)有一個或多個部件:如何在Rails COUNT列添加到工作查詢與組()3.1

class UserProfile < ActiveRecord::Base 
    has_many :widgets 
end 

@all_profiles = UserProfile.joins(:widgets).group('user_profiles.id').order("name ASC") 

在索引視圖,而不是在每個視圖行中執行新的查詢以獲得小部件的數量爲@all_profile.each,有沒有辦法給原始數據添加一個計數列,以顯示每個分組行中有多少個小部件? (例如,如果存在N個@all_profiles,避免再次查詢數據庫N次?

(這非常重要,不僅避免N個額外的查詢,還允許我們在count列上添加SORT選項,所以我們可以排序客戶提供最部件)

回答

11

您可以通過ActiveRecord::QueryMethods#select

@all_profiles = UserProfile.joins(:widgets).select('user_profiles.*, COUNT(*) AS widget_count').group('user_profiles.id').order('name ASC') 

現在添加一個COUNT列,每個返回的對象將包含一個widget_count屬性,你可以訪問就像任何其他的模型屬性:

@all_profiles.each do |profile| 
    puts profile.widget_count 
end 
+0

非常感謝你這麼詳細的答覆!完美工作。 (我以前曾嘗試將.select放在錯誤的位置) – jpwynn 2012-08-15 17:32:38

+0

雖然它在SQLITE3上正常工作,Postgres(Heroku)拋出一個錯誤:(PG :: Error:錯誤:列「widgets.id」必須出現在GROUP BY子句或在集合函數中使用)。用count(widgets.id)替換count(*),仍然可以在SQLITE上工作,但仍然會在Postgres上拋出相同的錯誤。我曾經想過使用rails activerecord抽象可以防止那些特定於dbase的問題。 – jpwynn 2012-08-15 17:48:10

+0

FWIW我們在heroku上使用postgres 9.1(新的基本計劃) – jpwynn 2012-08-15 18:16:38

0

可以使用計數方法,具有:組參數:count

這應該是這個樣子:

UserProfile.joins(:widgets).order(:name).count(:id, :group => 'user_profiles.id') 
+1

這只是返回一個哈希映射'UserProfile' ID到特定'UserProfile'的小部件計數。 OP要求將計數包括在原始查詢中,這樣除了計數之外,所有'UserProfile'屬性都會返回。 – Brandan 2012-08-15 21:02:56