From ea7191bdb22dae3eae1f41869f627877c19afee3 Mon Sep 17 00:00:00 2001 From: Gaspard Bucher Date: Tue, 10 Feb 2009 12:10:57 +0100 Subject: [PATCH] accepts_nested_attributes_for should not redefine the attribute writer if the method exists. --- .../lib/active_record/nested_attributes.rb | 12 +++++++----- activerecord/test/cases/nested_attributes_test.rb | 13 +++++++++---- activerecord/test/models/pirate.rb | 11 +++++++++++ 3 files changed, 27 insertions(+), 9 deletions(-) diff --git a/activerecord/lib/active_record/nested_attributes.rb b/activerecord/lib/active_record/nested_attributes.rb index 5778223..f99a6fe 100644 --- a/activerecord/lib/active_record/nested_attributes.rb +++ b/activerecord/lib/active_record/nested_attributes.rb @@ -181,11 +181,13 @@ module ActiveRecord # def pirate_attributes=(attributes) # assign_nested_attributes_for_one_to_one_association(:pirate, attributes, false) # end - class_eval %{ - def #{association_name}_attributes=(attributes) - assign_nested_attributes_for_#{type}_association(:#{association_name}, attributes, #{options[:allow_destroy]}) - end - }, __FILE__, __LINE__ + unless instance_methods.include?("#{association_name}_attributes=") + class_eval %{ + def #{association_name}_attributes=(attributes) + assign_nested_attributes_for_#{type}_association(:#{association_name}, attributes, #{options[:allow_destroy]}) + end + }, __FILE__, __LINE__ + end else raise ArgumentError, "No association found for name `#{association_name}'. Has it been defined yet?" end diff --git a/activerecord/test/cases/nested_attributes_test.rb b/activerecord/test/cases/nested_attributes_test.rb index 2e531a2..e0e17b2 100644 --- a/activerecord/test/cases/nested_attributes_test.rb +++ b/activerecord/test/cases/nested_attributes_test.rb @@ -43,9 +43,7 @@ class TestNestedAttributesInGeneral < ActiveRecord::TestCase end def test_should_disable_allow_destroy_by_default - Pirate.accepts_nested_attributes_for :ship - - pirate = Pirate.create!(:catchphrase => "Don' botharrr talkin' like one, savvy?") + pirate = SpecialPirate.create!(:catchphrase => "Don' botharrr talkin' like one, savvy?") ship = pirate.create_ship(:name => 'Nights Dirty Lightning') assert_no_difference('Ship.count') do @@ -70,7 +68,14 @@ class TestNestedAttributesOnAHasOneAssociation < ActiveRecord::TestCase def test_should_define_an_attribute_writer_method_for_the_association assert_respond_to @pirate, :ship_attributes= end - + + def test_should_not_redefine_an_attribute_writer_method_for_the_association + titanic = {'name' => 'Titanic', 'sunk' => true} + @pirate = SpecialPirate.new + @pirate.ship_attributes = titanic + assert_equal titanic, @pirate.special_ship_attributes + end + def test_should_automatically_instantiate_an_associated_model_if_there_is_none @ship.destroy @pirate.reload.ship_attributes = { :name => 'Davy Jones Gold Dagger' } diff --git a/activerecord/test/models/pirate.rb b/activerecord/test/models/pirate.rb index 6a2416a..03b622e 100644 --- a/activerecord/test/models/pirate.rb +++ b/activerecord/test/models/pirate.rb @@ -14,3 +14,14 @@ class Pirate < ActiveRecord::Base validates_presence_of :catchphrase end + +class SpecialPirate < ActiveRecord::Base + set_table_name 'pirates' + has_one :ship, :foreign_key => 'pirate_id' + attr_reader :special_ship_attributes + def ship_attributes=(attrs) + @special_ship_attributes = attrs + end + # accepts_nested_attributes_for called after "ship_attributes=" definition + accepts_nested_attributes_for :ship +end \ No newline at end of file -- 1.6.0