Permalink
Browse files

Saving a record with two unsaved belongs_to associations pointing to …

…the same object fails #2023 [Tobias Luetke]

git-svn-id: http://svn-commit.rubyonrails.org/rails/trunk@2040 5ecf4fe2-1ee6-0310-87b1-e25e094e27de
  • Loading branch information...
1 parent 2116171 commit dfe1aeb776ed9a7da8b431c7933c858d155a13c7 @jamis jamis committed Aug 23, 2005
View
@@ -1,5 +1,7 @@
*SVN*
+* Saving a record with two unsaved belongs_to associations pointing to the same object fails #2023 [Tobias Luetke]
+
* Make destroy return self #1913 [sebastian.kanthak@muehlheim.de]
* Fix typo in validations documentation #1938 [court3nay]
@@ -445,10 +445,12 @@ def belongs_to(association_id, options = {})
module_eval do
before_save <<-EOF
association = instance_variable_get("@#{association_name}")
- if not association.nil? and association.new_record?
- association.save(true)
+ if not association.nil?
+ if association.new_record?
+ association.save(true)
+ association.send(:construct_sql)
+ end
self["#{association_class_primary_key_name}"] = association.id
- association.send(:construct_sql)
end
EOF
end
@@ -5,6 +5,8 @@
require 'fixtures/topic'
require 'fixtures/reply'
require 'fixtures/computer'
+require 'fixtures/customer'
+require 'fixtures/order'
# Can't declare new classes in test case methods, so tests before that
bad_collection_keys = false
@@ -770,6 +772,45 @@ def xtest_counter_cache
apple.clients.to_s
assert_equal 1, apple.clients.size, "Should not use the cached number, but go to the database"
end
+
+ def test_store_two_association_with_one_save
+ num_orders = Order.count
+ num_customers = Customer.count
+ order = Order.new
+
+ customer1 = order.billing = Customer.new
+ customer2 = order.shipping = Customer.new
+ assert order.save
+ assert_equal customer1, order.billing
+ assert_equal customer2, order.shipping
+
+ order.reload
+
+ assert_equal customer1, order.billing
+ assert_equal customer2, order.shipping
+
+ assert_equal num_orders +1, Order.count
+ assert_equal num_customers +2, Customer.count
+ end
+
+ def test_store_association_in_two_relations_with_one_save
+ num_orders = Order.count
+ num_customers = Customer.count
+ order = Order.new
+
+ customer = order.billing = order.shipping = Customer.new
+ assert order.save
+ assert_equal customer, order.billing
+ assert_equal customer, order.shipping
+
+ order.reload
+
+ assert_equal customer, order.billing
+ assert_equal customer, order.shipping
+
+ assert_equal num_orders +1, Order.count
+ assert_equal num_customers +1, Customer.count
+ end
end
@@ -55,6 +55,14 @@ CREATE TABLE developers_projects (
access_level smallint default 1
);
+CREATE TABLE orders (
+ id int generated by default as identity (start with +10000),
+ name varchar(100) default NULL,
+ billing_customer_id int default NULL,
+ shipping_customer_id int default NULL,
+ PRIMARY KEY (id)
+);
+
CREATE TABLE customers (
id int generated by default as identity (start with +10000),
name varchar(100) default NULL,
@@ -56,6 +56,14 @@ CREATE TABLE `developers_projects` (
`access_level` smallint default 1
) TYPE=InnoDB;
+CREATE TABLE `orders` (
+ `id` int(11) NOT NULL auto_increment,
+ `name` varchar(100) default NULL,
+ `billing_customer_id` int(11) default NULL,
+ `shipping_customer_id` int(11) default NULL,
+ PRIMARY KEY (`id`)
+) TYPE=InnoDB;
+
CREATE TABLE `customers` (
`id` int(11) NOT NULL auto_increment,
`name` varchar(100) default NULL,
@@ -182,4 +190,4 @@ CREATE TABLE `fk_test_has_fk` (
`fk_id` INTEGER NOT NULL,
FOREIGN KEY (`fk_id`) REFERENCES `fk_test_has_pk`(`id`)
-) TYPE=InnoDB;
+) TYPE=InnoDB;
@@ -89,6 +89,15 @@ create table developers_projects (
);
create sequence developers_projects_seq minvalue 10000;
+create table orders (
+ id integer not null,
+ name varchar(100) default null,
+ billing_customer_id integer default null,
+ shipping_customer_id integer default null,
+ primary key (id)
+);
+create sequence orders_seq minvalue 10000;
+
create table customers (
id integer not null,
name varchar(100) default null,
@@ -72,6 +72,15 @@ CREATE TABLE customers (
);
SELECT setval('customers_id_seq', 100);
+CREATE TABLE orders (
+ id serial,
+ name character varying,
+ billing_customer_id integer,
+ shipping_customer_id integer,
+ PRIMARY KEY (id)
+);
+SELECT setval('orders_id_seq', 100);
+
CREATE TABLE movies (
movieid serial,
name text,
@@ -51,6 +51,14 @@ CREATE TABLE 'developers_projects' (
'access_level' INTEGER DEFAULT 1
);
+
+CREATE TABLE 'orders' (
+ 'id' INTEGER PRIMARY KEY NOT NULL,
+ 'name' VARCHAR(255) DEFAULT NULL,
+ 'billing_customer_id' INTEGER DEFAULT NULL,
+ 'shipping_customer_id' INTEGER DEFAULT NULL
+);
+
CREATE TABLE 'customers' (
'id' INTEGER PRIMARY KEY NOT NULL,
'name' VARCHAR(255) DEFAULT NULL,
@@ -50,6 +50,14 @@ CREATE TABLE developers_projects (
access_level int default 1
);
+CREATE TABLE orders (
+ id int NOT NULL IDENTITY(1, 1) PRIMARY KEY,
+ name varchar(100) default NULL,
+ billing_customer_id int default NULL,
+ shipping_customer_id int default NULL
+);
+
+
CREATE TABLE customers (
id int NOT NULL IDENTITY(1, 1) PRIMARY KEY,
name varchar(100) default NULL,
@@ -0,0 +1,4 @@
+class Order < ActiveRecord::Base
+ belongs_to :billing, :class_name => 'Customer', :foreign_key => 'billing_customer_id'
+ belongs_to :shipping, :class_name => 'Customer', :foreign_key => 'shipping_customer_id'
+end

0 comments on commit dfe1aeb

Please sign in to comment.