2009-10-14 5 views
3

Disons que j'ai des modèles qui ressemblent à ceci:Comment filtrer par nombre d'associations?

class Foo < ActiveRecord::Base 
    has_many :bars, :through => :cakes 
    has_many :cakes 
end 

class Bar < ActiveRecord::Base 
    has_many :foos, :through => :cakes 
    has_many :cakes 
end 

class Cake < ActiveRecord::Base 
    belongs_to :foo 
    belongs_to :bar 
end 

Comment puis-je obtenir tous les foos qui avaient plus de 10 bars (et donc plus de 10 gâteaux)?

Répondre

5
Foo.all(:joins => :cakes, 
    :group => "cakes.foo_id", 
    :having => "count(cakes.bar_id) >= 10") 
+4

Vous pouvez accélérer ce à l'aide d'un counter_cache. Foo.find (: all,: conditions => ['foo.cake_count> 10']) – jonnii

1

okay j'ai essayé la réponse ci-dessus, mais j'ai eu un problème.

pour nos besoins Père has_many: sons, ok? Je voulais trouver des pères qui n'avaient pas de fils.

ce qui précède n'a pas fonctionné, car il a produit une jointure interne ... filtrant ainsi tous les pères sans fils.

ce qui suit a travaillé pour moi:

Father.includes(:sons).group('fathers.id').having('count(sons.id)=0')

et il arrive aussi de travailler pour tout autre filtre que vous auriez besoin

Father.includes(:sons).group('fathers.id').having('count(sons.id)=3')

Questions connexes