From 3ba2733d72ab368bab70e1480fc0de6b434a28d0 Mon Sep 17 00:00:00 2001 From: Tim Chater Date: Tue, 17 Jun 2008 13:54:03 +0100 Subject: [PATCH] dirty fixed to record changes from zero to blank --- activerecord/lib/active_record/dirty.rb | 4 +++- activerecord/test/cases/dirty_test.rb | 27 +++++++++++++++++++++++++++ 2 files changed, 30 insertions(+), 1 deletions(-) diff --git a/activerecord/lib/active_record/dirty.rb b/activerecord/lib/active_record/dirty.rb index b32e17e..a7d7674 100644 --- a/activerecord/lib/active_record/dirty.rb +++ b/activerecord/lib/active_record/dirty.rb @@ -142,9 +142,11 @@ module ActiveRecord def field_changed?(attr, old, value) if column = column_for_attribute(attr) - if column.type == :integer && column.null && old.nil? + if column.type == :integer && column.null && (old.nil? || old == 0) # For nullable integer columns, NULL gets stored in database for blank (i.e. '') values. # Hence we don't record it as a change if the value changes from nil to ''. + # If an old value of 0 is set to '' we want this to get changed to nil as otherwise it'll + # be typecast back to 0 (''.to_i => 0) value = nil if value.blank? else value = column.type_cast(value) diff --git a/activerecord/test/cases/dirty_test.rb b/activerecord/test/cases/dirty_test.rb index c011ffa..4fceef2 100644 --- a/activerecord/test/cases/dirty_test.rb +++ b/activerecord/test/cases/dirty_test.rb @@ -53,6 +53,33 @@ class DirtyTest < ActiveRecord::TestCase assert_nil pirate.parrot_id_change end end + + def test_zero_to_blank_marked_as_changed + pirate = Pirate.new + pirate.catchphrase = "Yarrrr, me hearties" + pirate.parrot_id = 1 + pirate.save + + # check the change from 1 to '' + pirate = Pirate.find_by_catchphrase("Yarrrr, me hearties") + pirate.parrot_id = '' + assert pirate.parrot_id_changed? + assert_equal([1, nil], pirate.parrot_id_change) + pirate.save + + # check the change from nil to 0 + pirate = Pirate.find_by_catchphrase("Yarrrr, me hearties") + pirate.parrot_id = 0 + assert pirate.parrot_id_changed? + assert_equal([nil, 0], pirate.parrot_id_change) + pirate.save + + # check the change from 0 to '' + pirate = Pirate.find_by_catchphrase("Yarrrr, me hearties") + pirate.parrot_id = '' + assert pirate.parrot_id_changed? + assert_equal([0, nil], pirate.parrot_id_change) + end def test_object_should_be_changed_if_any_attribute_is_changed pirate = Pirate.new -- 1.5.5.1