aboutsummaryrefslogtreecommitdiffstats
path: root/activerecord
diff options
context:
space:
mode:
authorAdam Gamble <adamgamble@gmail.com>2013-01-31 21:54:41 -0600
committerAdam Gamble <adamgamble@gmail.com>2013-03-14 12:46:50 -0500
commit8fccbc1ad4fff215c63d17b9321fc69ad17e89dc (patch)
treedddbd457a233d509f912d0850ca9d6162e8624e4 /activerecord
parent7fc339059cbace0af8f8dbfb5c68db3f5dffd5a3 (diff)
downloadrails-8fccbc1ad4fff215c63d17b9321fc69ad17e89dc.tar.gz
rails-8fccbc1ad4fff215c63d17b9321fc69ad17e89dc.tar.bz2
rails-8fccbc1ad4fff215c63d17b9321fc69ad17e89dc.zip
Modifies belong_to touch callback to touch old associations also #9091
Diffstat (limited to 'activerecord')
-rw-r--r--activerecord/CHANGELOG.md22
-rw-r--r--activerecord/lib/active_record/associations/builder/belongs_to.rb10
-rw-r--r--activerecord/test/cases/timestamp_test.rb12
3 files changed, 34 insertions, 10 deletions
diff --git a/activerecord/CHANGELOG.md b/activerecord/CHANGELOG.md
index f73fc9d9a3..7dbfad4473 100644
--- a/activerecord/CHANGELOG.md
+++ b/activerecord/CHANGELOG.md
@@ -447,6 +447,28 @@
*Aaron Stone + Rafael Mendonça França*
* `Relation#merge` now only overwrites where values on the LHS of the
+=======
+* Belongs_to :touch behavior now touches old association when
+ transitioning to new association
+
+ class Passenger < ActiveRecord::Base
+ belongs_to :car, touch: true
+ end
+
+ car_1 = Car.create
+ car_2 = Car.create
+
+ passenger = Passenger.create :car => car_1
+
+ passenger.car = car_2
+ passenger.save
+
+ Previously only car_2 would be touched. Now both car_1 and car_2
+ will be touched.
+
+ *Adam Gamble*
+
+* Relation#merge now only overwrites where values on the LHS of the
merge. Consider:
left = Person.where(age: [13, 14, 15])
diff --git a/activerecord/lib/active_record/associations/builder/belongs_to.rb b/activerecord/lib/active_record/associations/builder/belongs_to.rb
index 97b1ff18e2..6b479968c8 100644
--- a/activerecord/lib/active_record/associations/builder/belongs_to.rb
+++ b/activerecord/lib/active_record/associations/builder/belongs_to.rb
@@ -48,6 +48,16 @@ module ActiveRecord::Associations::Builder
def belongs_to_touch_after_save_or_destroy_for_#{name}
record = #{name}
+ foreign_key_field = #{reflection.foreign_key}
+ if changed_attributes.key?(foreign_key_field)
+ reflection_klass = #{reflection.klass}
+ old_foreign_id = changed_attributes[foreign_key_field]
+ old_record = reflection_klass.where(foreign_key_field.to_sym => old_foreign_id).first
+ if old_record
+ old_record.touch #{options[:touch].inspect if options[:touch] != true}
+ end
+ end
+
unless record.nil? || record.new_record?
record.touch #{options[:touch].inspect if options[:touch] != true}
end
diff --git a/activerecord/test/cases/timestamp_test.rb b/activerecord/test/cases/timestamp_test.rb
index 6f983bce75..0c13bb946a 100644
--- a/activerecord/test/cases/timestamp_test.rb
+++ b/activerecord/test/cases/timestamp_test.rb
@@ -176,7 +176,7 @@ class TimestampTest < ActiveRecord::TestCase
assert_not_equal time, owner.updated_at
end
- def test_changing_parent_of_a_record_touches_both_new_and_old_parent_record_and_grandparent_record
+ def test_changing_parent_of_a_record_touches_both_new_and_old_parent_record
klass = Class.new(ActiveRecord::Base) do
def self.name; 'Toy'; end
belongs_to :pet, touch: true
@@ -184,30 +184,22 @@ class TimestampTest < ActiveRecord::TestCase
toy1 = klass.find(1)
old_pet = toy1.pet
- old_owner = old_pet.owner
toy2 = klass.find(2)
new_pet = toy2.pet
- new_owner = new_pet.owner
time = 3.days.ago
old_pet.update_columns(updated_at: time)
- old_owner.update_columns(updated_at: time)
new_pet.update_columns(updated_at: time)
- new_owner.update_columns(updated_at: time)
toy1.pet = new_pet
toy1.save!
old_pet.reload
- old_owner.reload
new_pet.reload
- new_owner.reload
- assert_not_equal time, old_pet.updated_at
- assert_not_equal time, old_owner.updated_at
assert_not_equal time, new_pet.updated_at
- assert_not_equal time, new_owner.updated_at
+ assert_not_equal time, old_pet.updated_at
end
def test_timestamp_attributes_for_create