wake-up-neo.net

Rails 3 - Auswahl mit Include?

Hier ist ein verschachteltes select mit include:

@items = Item.where("complete = ?", true).includes( :manufacturer, {:order=>[:supplier, :agent] })

Dies ist eine Steuerabfrage, da aus allen oben enthaltenen Tabellen Tausende von Datenzeilen abgerufen werden.

Wie kann ich mit der Abfrage nur bestimmte Felder auswählen?

  • user.name, user.created_at
  • order.created_at
  • name des Anbieters
  • agent.name
  • herstellername
37
sscirrus

Es gibt eine select-Methode in ARel, aber Sie müssen die korrekten Tabellennamen verwenden (d. H. Plural und Vorsicht, wenn Sie polymorphe Modelle verwenden oder set_table_name oder eine andere ähnliche nicht standardmäßige Vorgehensweise verwenden).

@items = Item.
  select('users.name', 'users.created_at', 'orders.created_at', 'suppliers.name', 'agents.name', 'manufacturers.name').
  where(:users => { :fulfilled => true }).
  includes(:orders => [:supplier, :agent], :manufacturer)

Msgstr "Wir können select mit Verknüpfungen verwenden, die nicht einschließen" - @ Bhavesh_A_P

Hinweis:

Wie @Bhavesh_A_P oben ausgeführt hat, führt select mit includes nicht zu einem konsistenten Verhalten. Es scheint, dass select ordnungsgemäß funktioniert, wenn die eingeschlossene Assoziation keine Ergebnisse zurückgibt. Wenn sie Ergebnisse zurückgibt, hat die select-Anweisung keine Auswirkung. Tatsächlich wird es vollständig ignoriert, sodass Ihre select-Anweisung auf ungültige Tabellennamen verweisen kann und kein Fehler erzeugt wird. select mit joins führt zu konsistentem Verhalten.

32

Eigentlich können wir select nicht mit include verwenden. Es kann nur mit Joins verwendet werden.

17
Bhaveshkumar

Das Problem wird nicht gelöst, indem ein Aufruf der Select-Methode in die Kette aufgenommen wird. In einem ähnlichen ActiveRecord :: Relation, das wir erstellt haben, scheint das Aufrufen von 'include' jeden Aufruf von 'select' zu überschreiben. 

scope :active, where("hired_on < ? AND (separated_on > ? OR separated_on IS NULL)", Time.now, Time.now )

scope :with_role, lambda {|roles| includes(:team_member_roles).where(:team_member_roles => {:role => roles } ) }

scope :with_site_code, lambda {|site_codes| includes(:team_member_sites).where(:team_member_sites => {:site_code => site_codes } ) }

TeamMember.select("team_members.email, team_members.first_name, team_members.last_name").active.with_site_code(params[:site_code]).with_role(["senior_editing", "senior_and_reg_editing"]) 

Wie gezeigt, wählt die Abfrage alle Spalten aus.

Wenn die beiden Bereiche "Joins" anstelle von "Includes" verwenden, funktioniert die Abfrage: Es werden nur die drei angegebenen Spalten ausgewählt.

5
Byofuel
Item.where("fulfilled = ?", true)
    .includes({:orders =>[:suppliers, :agents]}, :manufacturers)
    .select("users.name, users.created_at, orders.created_at, suppliers.name, agents.name").
    .order('orders.created_at DESC')
0
Moin Haidar