2010-11-16 12 views
10

Okay, ich bin auf diesem einen gründlich überstürzt. Ich versuche ein Menü mit veröffentlichten Webseiten nach Kategorien geordnet zu erstellen.Rails 3 - Eager Laden mit Bedingungen

Category.rb:

belongs_to :parent, :class_name => "Category", :foreign_key => "parent_id" 
has_many :children, :class_name => "Category", :foreign_key => "parent_id" 
has_many :pages, :documents, :galleries 

Page.rb

belongs_to :category 

Die Seite Modell auch hat: is_published, so versuche ich, auch auf das filtern. Ich bin nur ungern meine schwache Abfrage versucht zu schreiben, aber keine andere Lösung sehen als viel intelligentere Menschen zu bitten:

(Selbst ist @current_website)

self.categories.includes(:children, :pages).where('pages.is_published = 1') 

Dies gibt vor allem, was ich brauche, aber nicht Elternteil Kategorien ohne veröffentlichte Seiten. Zum Beispiel, es funktioniert großartig, wenn ich:

Parent Category 
- Published Page 
- Child Category 
-- Published Page 

Wo es nicht ist, wenn ich keine veröffentlichten Seiten im Elternteil haben, wie folgt aus:

Parent Category 
- Child Category 
-- Published Page 
- Child Category 
-- Published Page 

Vielen Dank im Voraus für jede Hilfe zu diesem Thema. Ich versuche so viel wie möglich über Abfragen zu lernen, aber ich bin gegen die Wand.

UPDATE: Implementieren KandadaBoggu Vorschlag viel bessere Ergebnisse erbracht hat, wurde dieser

has_many :published_pages, :class_name => "Page", 
          :conditions => {:is_published => true} 

jedoch zu Category.rb hinzugefügt, wenn die folgende Verwendung:

self.categories.where(:parent_id => nil).includes({:children => :published_pages}, 
                :published_pages) 

ich die Ergebnisse, ich brauche, aber ich bekomme auch leere Elternkategorien (keine published_pages, keine untergeordneten Kategorien mit veröffentlichten Seiten. Ein Beispiel:

- Parent Category 
-- Published Page 
- Parent Category 
-- NOTHING 

Meine temporäre Lösung war die Abfrage mit der beigefügten:

reject{|category| category.pages.empty? && category.children.empty?} 

Danke für Ihre Hilfe wieder.

Antwort

14

ein neuer Verein hinzufügen genannt published_pages (abgesehen von der aktuellen Assoziationen)

class Category 

    has_many :children,  :class_name => "Category", 
       :foreign_key => "parent_id" 
    has_many :published_pages, :class_name => "Page", 
       :conditions => { :is_published => true } 

end 

Jetzt können Sie alle Kategorien erhalten wie folgt:

self.categories.includes(:children, :published_pages) 

Wenn Sie lernen, warum Ihr Ansatz interessiert sind hat nicht funktioniert, lesen Sie die Schienen documentation (scrollen 10-15 Zeilen nach dem Eager loading of associations Abschnitt).Ich habe den entsprechenden Code-Schnipsel unten enthalten:

Zum Beispiel

Post.includes([:author, :comments]).where(['comments.approved = ?', true]).all 

Dies in einer einzigen SQL-Abfrage führt mit entlang der Linien verbindet:

LEFT OUTER JOIN comments ON comments.post_id = posts.id and 
LEFT OUTER JOIN authors ON authors.id = posts.author_id. 

Beachten Sie, dass unter Verwendung von Bedingungen wie Dies kann unbeabsichtigte Folgen haben. Im obigen Beispiel werden Beiträge mit genehmigten Kommentaren überhaupt nicht zurückgegeben , weil die Bedingungen gelten für die SQL-Anweisung als Ganzes und nicht nur für die Zuordnung. Sie müssen die Spalte Referenzen für diesen Fallback disambiguieren, zum Beispiel: order => "author.name DESC" wird funktionieren, aber: order => "name DESC" wird nicht.

Um eifrig Last gefilterten Zeilen eines Vereins, eine Assoziation mit Bedingungen verwenden:

class Post < ActiveRecord::Base 
    has_many :approved_comments, :class_name => 'Comment', 
      :conditions => ['approved = ?', true] 
end 

Post.find(:all, :include => :approved_comments) 
+0

Danke für die meisten ausgezeichnete Zuschreibung, Link und Erklärung, KandadaBoggu! Dies hat mich auf den richtigen Weg gebracht, ich habe immer noch ein Problem mit self.categories.includes (: children =>: published_pages,: published_pages), die Eltern ohne Seiten oder Kinderkategorien mit Seiten liefert. DANKE NOCH EINMAL! – TMB

+0

Aktualisieren Sie Ihre Frage und spezifizieren Sie Ihre Anforderung w.r.t zur Anwesenheit/Abwesenheit von Seiten. –

+0

Fantasisch hilfreich danke - zog meine Haare aus – jpwynn

Verwandte Themen