mirror of
https://github.com/rails/rails.git
synced 2022-11-09 12:12:34 -05:00
Allow extra scoping in callbacks when create on association relation
#37523 has a regression that ignore extra scoping in callbacks when create on association relation. It should respect `klass.current_scope` even when create on association relation to allow extra scoping in callbacks. Fixes #38741.
This commit is contained in:
parent
8544c9c236
commit
f64b5fb942
4 changed files with 28 additions and 19 deletions
|
@ -17,24 +17,18 @@ module ActiveRecord
|
|||
|
||||
def build(attributes = nil, &block)
|
||||
block = _deprecated_scope_block("new", &block)
|
||||
@association.scoping(self) do
|
||||
@association.build(attributes, &block)
|
||||
end
|
||||
scoping { @association.build(attributes, &block) }
|
||||
end
|
||||
alias new build
|
||||
|
||||
def create(attributes = nil, &block)
|
||||
block = _deprecated_scope_block("create", &block)
|
||||
@association.scoping(self) do
|
||||
@association.create(attributes, &block)
|
||||
end
|
||||
scoping { @association.create(attributes, &block) }
|
||||
end
|
||||
|
||||
def create!(attributes = nil, &block)
|
||||
block = _deprecated_scope_block("create!", &block)
|
||||
@association.scoping(self) do
|
||||
@association.create!(attributes, &block)
|
||||
end
|
||||
scoping { @association.create!(attributes, &block) }
|
||||
end
|
||||
|
||||
private
|
||||
|
|
|
@ -41,7 +41,6 @@ module ActiveRecord
|
|||
reflection.check_validity!
|
||||
|
||||
@owner, @reflection = owner, reflection
|
||||
@_scope = nil
|
||||
|
||||
reset
|
||||
reset_scope
|
||||
|
@ -98,7 +97,11 @@ module ActiveRecord
|
|||
end
|
||||
|
||||
def scope
|
||||
@_scope&.spawn || target_scope.merge!(association_scope)
|
||||
if (scope = klass.current_scope) && scope.try(:proxy_association) == self
|
||||
scope.spawn
|
||||
else
|
||||
target_scope.merge!(association_scope)
|
||||
end
|
||||
end
|
||||
|
||||
def reset_scope
|
||||
|
@ -198,13 +201,6 @@ module ActiveRecord
|
|||
_create_record(attributes, true, &block)
|
||||
end
|
||||
|
||||
def scoping(relation, &block)
|
||||
@_scope = relation
|
||||
relation.scoping(&block)
|
||||
ensure
|
||||
@_scope = nil
|
||||
end
|
||||
|
||||
private
|
||||
def find_target
|
||||
if owner.strict_loading?
|
||||
|
|
|
@ -224,6 +224,18 @@ class HasManyAssociationsTest < ActiveRecord::TestCase
|
|||
def test_build_and_create_from_association_should_respect_passed_attributes_over_default_scope
|
||||
car = Car.create(name: "honda")
|
||||
|
||||
bulb = car.bulbs.where(name: "exotic").build
|
||||
assert_equal "exotic", bulb.name
|
||||
assert_nil bulb.count_after_create
|
||||
|
||||
bulb = car.bulbs.where(name: "exotic").create
|
||||
assert_equal "exotic", bulb.name
|
||||
assert_equal 1, bulb.count_after_create
|
||||
|
||||
bulb = car.bulbs.where(name: "exotic").create!
|
||||
assert_equal "exotic", bulb.name
|
||||
assert_equal 2, bulb.count_after_create
|
||||
|
||||
bulb = car.bulbs.build(name: "exotic")
|
||||
assert_equal "exotic", bulb.name
|
||||
|
||||
|
|
|
@ -5,7 +5,7 @@ class Bulb < ActiveRecord::Base
|
|||
belongs_to :car, touch: true
|
||||
scope :awesome, -> { where(frickinawesome: true) }
|
||||
|
||||
attr_reader :scope_after_initialize, :attributes_after_initialize
|
||||
attr_reader :scope_after_initialize, :attributes_after_initialize, :count_after_create
|
||||
|
||||
after_initialize :record_scope_after_initialize
|
||||
def record_scope_after_initialize
|
||||
|
@ -17,6 +17,13 @@ class Bulb < ActiveRecord::Base
|
|||
@attributes_after_initialize = attributes.dup
|
||||
end
|
||||
|
||||
after_create :record_count_after_create
|
||||
def record_count_after_create
|
||||
@count_after_create = Bulb.unscoped do
|
||||
car&.bulbs&.count
|
||||
end
|
||||
end
|
||||
|
||||
def color=(color)
|
||||
self[:color] = color.upcase + "!"
|
||||
end
|
||||
|
|
Loading…
Reference in a new issue