aboutsummaryrefslogtreecommitdiffstats
path: root/activerecord/lib
diff options
context:
space:
mode:
authorDavid Heinemeier Hansson <david@loudthinking.com>2005-04-19 16:32:57 +0000
committerDavid Heinemeier Hansson <david@loudthinking.com>2005-04-19 16:32:57 +0000
commit6f34400086857bf1ed790e8a46f10be5debe5d53 (patch)
tree4edce4e9dea167912cf54d1e2568d800d426fbe1 /activerecord/lib
parent71a616890bb3557764d6a6731fd3ec9e63220a5b (diff)
downloadrails-6f34400086857bf1ed790e8a46f10be5debe5d53.tar.gz
rails-6f34400086857bf1ed790e8a46f10be5debe5d53.tar.bz2
rails-6f34400086857bf1ed790e8a46f10be5debe5d53.zip
Fixed order of loading in eager associations
git-svn-id: http://svn-commit.rubyonrails.org/rails/trunk@1229 5ecf4fe2-1ee6-0310-87b1-e25e094e27de
Diffstat (limited to 'activerecord/lib')
-rwxr-xr-xactiverecord/lib/active_record/associations.rb26
-rw-r--r--activerecord/lib/active_record/associations/association_proxy.rb4
2 files changed, 20 insertions, 10 deletions
diff --git a/activerecord/lib/active_record/associations.rb b/activerecord/lib/active_record/associations.rb
index 5f206f5472..017689b9cd 100755
--- a/activerecord/lib/active_record/associations.rb
+++ b/activerecord/lib/active_record/associations.rb
@@ -147,7 +147,10 @@ module ActiveRecord
# :limit property and it will be ignored if attempted.
#
# Also have in mind that since the eager loading is pulling from multiple tables, you'll have to disambiguate any column references
- # in both conditions and orders. So :order => "posts.id DESC" will work while :order => "id DESC" will not.
+ # in both conditions and orders. So :order => "posts.id DESC" will work while :order => "id DESC" will not. This may require that
+ # you alter the :order and :conditions on the association definitions themselves.
+ #
+ # It's currently not possible to use eager loading on multiple associations from the same table.
#
# == Modules
#
@@ -690,24 +693,26 @@ module ActiveRecord
primary_key_table = generate_primary_key_table(reflections, schema_abbreviations)
rows = select_all_rows(options, schema_abbreviations, reflections)
- records = { }
+ records, records_in_order = { }, []
primary_key = primary_key_table[table_name]
for row in rows
id = row[primary_key]
- records[id] ||= instantiate(extract_record(schema_abbreviations, table_name, row))
-
+ records_in_order << (records[id] = instantiate(extract_record(schema_abbreviations, table_name, row))) unless records[id]
+ record = records[id]
+
reflections.each do |reflection|
next unless row[primary_key_table[reflection.table_name]]
case reflection.macro
when :has_many, :has_and_belongs_to_many
- records[id].send(reflection.name)
- records[id].instance_variable_get("@#{reflection.name}").target.push(
- reflection.klass.send(:instantiate, extract_record(schema_abbreviations, reflection.table_name, row))
- )
+ collection = record.send(reflection.name)
+ collection.loaded
+
+ association = reflection.klass.send(:instantiate, extract_record(schema_abbreviations, reflection.table_name, row))
+ collection.target.push(association) unless collection.target.include?(association)
when :has_one, :belongs_to
- records[id].send(
+ record.send(
"#{reflection.name}=",
reflection.klass.send(:instantiate, extract_record(schema_abbreviations, reflection.table_name, row))
)
@@ -715,9 +720,10 @@ module ActiveRecord
end
end
- return records.values
+ return records_in_order
end
+
def reflect_on_included_associations(associations)
[ associations ].flatten.collect { |association| reflect_on_association(association) }
end
diff --git a/activerecord/lib/active_record/associations/association_proxy.rb b/activerecord/lib/active_record/associations/association_proxy.rb
index 8548848e4f..f80a7e996c 100644
--- a/activerecord/lib/active_record/associations/association_proxy.rb
+++ b/activerecord/lib/active_record/associations/association_proxy.rb
@@ -32,6 +32,10 @@ module ActiveRecord
@loaded
end
+ def loaded
+ @loaded = true
+ end
+
def target
@target
end