From 3b4b6108ac395d35f3bcfe5667aba13f323b1789 Mon Sep 17 00:00:00 2001 From: Grant Hollingworth Date: Tue, 25 Nov 2008 05:52:36 -0500 Subject: [PATCH] set multiparameter to nil if any parts of it are empty --- activerecord/lib/active_record/base.rb | 18 +++++++++++++----- activerecord/test/cases/base_test.rb | 13 +++++++++---- 2 files changed, 22 insertions(+), 9 deletions(-) diff --git a/activerecord/lib/active_record/base.rb b/activerecord/lib/active_record/base.rb index 9e45143..4abc294 100755 --- a/activerecord/lib/active_record/base.rb +++ b/activerecord/lib/active_record/base.rb @@ -2915,16 +2915,24 @@ module ActiveRecord #:nodoc: attribute_name = multiparameter_name.split("(").first attributes[attribute_name] = [] unless attributes.include?(attribute_name) - unless value.empty? - attributes[attribute_name] << - [ find_parameter_position(multiparameter_name), type_cast_attribute_value(multiparameter_name, value) ] - end + attributes[attribute_name] << + [ find_parameter_position(multiparameter_name), type_cast_attribute_value(multiparameter_name, value) ] end - attributes.each { |name, values| attributes[name] = values.sort_by{ |v| v.first }.collect { |v| v.last } } + attributes.each do |name, values| + attributes[name] = if values.collect {|v| v.last }.include?(nil) + [] + else + values.sort_by {|v| v.first}.collect { |v| v.last } + end + end end def type_cast_attribute_value(multiparameter_name, value) + value.empty? ? nil : type_cast_attribute_non_empty_value(multiparameter_name, value) + end + + def type_cast_attribute_non_empty_value(multiparameter_name, value) multiparameter_name =~ /\([0-9]*([a-z])\)/ ? value.send("to_" + $1) : value end diff --git a/activerecord/test/cases/base_test.rb b/activerecord/test/cases/base_test.rb index 5f54931..64919b6 100755 --- a/activerecord/test/cases/base_test.rb +++ b/activerecord/test/cases/base_test.rb @@ -1008,9 +1008,14 @@ class BasicsTest < ActiveRecord::TestCase attributes = { "last_read(1i)" => "2004", "last_read(2i)" => "6", "last_read(3i)" => "" } topic = Topic.find(1) topic.attributes = attributes - # note that extra #to_date call allows test to pass for Oracle, which - # treats dates/times the same - assert_date_from_db Date.new(2004, 6, 1), topic.last_read.to_date + assert_nil topic.last_read + end + + def test_multiparameter_attributes_on_date_with_empty_year + attributes = { "last_read(1i)" => "", "last_read(2i)" => "6", "last_read(3i)" => "1" } + topic = Topic.find(1) + topic.attributes = attributes + assert_nil topic.last_read end def test_multiparameter_attributes_on_date_with_all_empty @@ -1133,7 +1138,7 @@ class BasicsTest < ActiveRecord::TestCase } topic = Topic.find(1) topic.attributes = attributes - assert_equal Time.local(2004, 6, 24, 16, 24, 0), topic.written_on + assert_nil topic.written_on end def test_multiparameter_mass_assignment_protector -- 1.6.0.2