From 8bb553701aca3e293e8f443cce58b294764ef8e1 Mon Sep 17 00:00:00 2001 From: Matchu Date: Fri, 25 Jan 2013 15:23:48 -0600 Subject: [PATCH] remove N+1 queries in contributions#index --- app/controllers/contributions_controller.rb | 9 ++++++++- app/models/contribution.rb | 17 +++++++---------- 2 files changed, 15 insertions(+), 11 deletions(-) diff --git a/app/controllers/contributions_controller.rb b/app/controllers/contributions_controller.rb index 20a4f8e9..2d37be10 100644 --- a/app/controllers/contributions_controller.rb +++ b/app/controllers/contributions_controller.rb @@ -7,6 +7,13 @@ class ContributionsController < ApplicationController @contributions = Contribution.includes(:user) end @contributions = @contributions.recent.paginate :page => params[:page] - Contribution.preload_contributeds_and_parents @contributions + Contribution.preload_contributeds_and_parents( + @contributions, + :scopes => { + 'Item' => Item.includes(:translations), + 'PetType' => PetType.includes({:species => :translations, + :color => :translations}) + } + ) end end diff --git a/app/models/contribution.rb b/app/models/contribution.rb index 648be077..6ce7d4f1 100644 --- a/app/models/contribution.rb +++ b/app/models/contribution.rb @@ -26,12 +26,9 @@ class Contribution < ActiveRecord::Base } CONTRIBUTED_CHILDREN = CONTRIBUTED_RELATIONSHIPS.keys CONTRIBUTED_TYPES = CONTRIBUTED_CHILDREN + CONTRIBUTED_RELATIONSHIPS.values - CONTRIBUTED_BASES = {} - CONTRIBUTED_TYPES.each do |type| - base = type == 'SwfAsset' ? SwfAsset.object_assets : type.constantize - CONTRIBUTED_BASES[type] = base - end - def self.preload_contributeds_and_parents(contributions) + def self.preload_contributeds_and_parents(contributions, options={}) + options[:scopes] ||= {} + # Initialize the groups we'll be using for quick access contributions_by_type = {} contributed_by_type = {} @@ -56,8 +53,8 @@ class Contribution < ActiveRecord::Base # Load contributed objects without parents, prepare them for easy access # for future assignment to contributions and looking up parents CONTRIBUTED_CHILDREN.each do |type| - base = CONTRIBUTED_BASES[type] - base.find(needed_ids_by_type[type]).each do |contributed| + scope = options[:scopes][type] || type.constantize.scoped + scope.find(needed_ids_by_type[type]).each do |contributed| contributed_by_type[type] << contributed contributed_by_type_and_id[type][contributed.id] = contributed end @@ -67,10 +64,10 @@ class Contribution < ActiveRecord::Base # contributed objects of that class. all_by_ids_or_children properly # assigns parents to children, as well CONTRIBUTED_RELATIONSHIPS.each do |child_type, type| - base = CONTRIBUTED_BASES[type] + scope = options[:scopes][type] || type.constantize.scoped ids = needed_ids_by_type[type] children = contributed_by_type[child_type] - base.all_by_ids_or_children(ids, children).each do |contributed| + scope.all_by_ids_or_children(ids, children).each do |contributed| contributed_by_type_and_id[type][contributed.id] = contributed end end