Skip to content

Commit 1a723c6

Browse files
committed
Should work inverse association when eager loading
This regression was caused by caa178c. The block for `set_inverse_instance` should also be passed to join dependency. Fixes rails#30402.
1 parent cb5af0d commit 1a723c6

File tree

4 files changed

+24
-15
lines changed

4 files changed

+24
-15
lines changed

activerecord/lib/active_record/associations/join_dependency.rb

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -119,15 +119,15 @@ def join_constraints(joins_to_add, join_type)
119119
end
120120

121121
def aliases
122-
Aliases.new join_root.each_with_index.map { |join_part, i|
122+
@aliases ||= Aliases.new join_root.each_with_index.map { |join_part, i|
123123
columns = join_part.column_names.each_with_index.map { |column_name, j|
124124
Aliases::Column.new column_name, "t#{i}_r#{j}"
125125
}
126126
Aliases::Table.new(join_part, columns)
127127
}
128128
end
129129

130-
def instantiate(result_set, aliases)
130+
def instantiate(result_set, &block)
131131
primary_key = aliases.column_alias(join_root, join_root.primary_key)
132132

133133
seen = Hash.new { |i, object_id|
@@ -150,7 +150,7 @@ def instantiate(result_set, aliases)
150150
message_bus.instrument("instantiation.active_record", payload) do
151151
result_set.each { |row_hash|
152152
parent_key = primary_key ? row_hash[primary_key] : row_hash
153-
parent = parents[parent_key] ||= join_root.instantiate(row_hash, column_aliases)
153+
parent = parents[parent_key] ||= join_root.instantiate(row_hash, column_aliases, &block)
154154
construct(parent, join_root, row_hash, result_set, seen, model_cache, aliases)
155155
}
156156
end

activerecord/lib/active_record/relation.rb

Lines changed: 14 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -566,7 +566,7 @@ def to_sql
566566
relation = self
567567

568568
if eager_loading?
569-
find_with_associations { |rel| relation = rel }
569+
find_with_associations { |rel, _| relation = rel }
570570
end
571571

572572
conn = klass.connection
@@ -660,7 +660,19 @@ def has_join_values?
660660

661661
def exec_queries(&block)
662662
skip_query_cache_if_necessary do
663-
@records = eager_loading? ? find_with_associations.freeze : @klass.find_by_sql(arel, &block).freeze
663+
@records =
664+
if eager_loading?
665+
find_with_associations do |relation, join_dependency|
666+
if ActiveRecord::NullRelation === relation
667+
[]
668+
else
669+
rows = connection.select_all(relation.arel, "SQL")
670+
join_dependency.instantiate(rows, &block)
671+
end.freeze
672+
end
673+
else
674+
klass.find_by_sql(arel, &block).freeze
675+
end
664676

665677
preload = preload_values
666678
preload += includes_values unless eager_loading?

activerecord/lib/active_record/relation/finder_methods.rb

Lines changed: 1 addition & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -372,16 +372,7 @@ def find_with_associations
372372
relation = select aliases.columns
373373
relation = apply_join_dependency(relation, join_dependency)
374374

375-
if block_given?
376-
yield relation
377-
else
378-
if ActiveRecord::NullRelation === relation
379-
[]
380-
else
381-
rows = skip_query_cache_if_necessary { connection.select_all(relation.arel, "SQL") }
382-
join_dependency.instantiate(rows, aliases)
383-
end
384-
end
375+
yield relation, join_dependency
385376
end
386377

387378
def construct_relation_for_exists(relation, conditions)

activerecord/test/cases/associations/eager_test.rb

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,12 @@ def test_eager_with_has_one_through_join_model_with_conditions_on_the_through
4040
assert_nil member.favourite_club
4141
end
4242

43+
def test_should_work_inverse_of_with_eager_load
44+
author = authors(:david)
45+
assert_same author, author.posts.first.author
46+
assert_same author, author.posts.eager_load(:comments).first.author
47+
end
48+
4349
def test_loading_with_one_association
4450
posts = Post.all.merge!(includes: :comments).to_a
4551
post = posts.find { |p| p.id == 1 }

0 commit comments

Comments
 (0)