[英]How to accumulate an array of all Active Record objects that are interconnected via “has_many” through relationships in Rails
[英]When are Active Record objects in has_many relationships saved?
我正在使用Rails 1.2.3(是的,我知道)並且對於has_many
如何在對象持久性方面起作用感到困惑。
為了舉例,我將使用它作為我的聲明:
class User < ActiveRecord::Base
has_many :assignments
end
class Assignment < ActiveRecord::Base
belongs_to :user
end
根據我的理解,這會生成一個方法User#assignments.build
,它創建一個Assignment
對象,其user_id
是接收實例的id
(並且其他字段在參數中指定),但不保存此對象在數據庫中。 稍后可以通過調用Assignment#save!
保存該對象Assignment#save!
。
然而,我一直用作教程和參考的實用程序員使用Rails的Agile Web開發第二版說:
如果父對象存在於數據庫中,則將子對象添加到集合會自動保存該子對象。
這里似乎有矛盾。 我想知道的是:
some_user.assignments.build
,是否保存了Assignment
對象? some_user.assignments << Assignment.new
,是否保存了Assignment
對象? some_user.assignments << Assignment.create
,是兩個數據庫調用,還是只有一個? 如果我在創建它之間修改Assignment
對象並將其添加到some_user.assignments
呢? save!
會怎么樣save!
一個Assignment
對象,其相應的User
尚未保存在數據庫中? PS我之所以不僅僅使用User#assignments.create
的原因是因為它不允許我將初始化擴展到外部方法,我希望能夠做到這一點。 我也不想多次去數據庫。
注意:下面的所有控制台測試都在Rails 3中運行。您可能會在Rails 1中獲得不同的輸出,您必須自己運行測試才能進行比較。
如果您想了解使用Active Record在幕后發生的事情,那么使用rails控制台非常有價值。 以下是未保存對象的情況:
u = User.new
#<User id: nil, name: nil, created_at: nil, updated_at: nil>
u.assignments.build(:name => "example")
#<Assignment id: nil, name: "example", user_id: nil, created_at: nil, updated_at: nil>
u.save
#SQL (0.2ms) INSERT INTO `users` (`created_at`, `name`, `updated_at`) VALUES ('2012-06-01 19:25:45', NULL, '2012-06-01 19:25:45')
#SQL (0.2ms) INSERT INTO `assignments` (`created_at`, `name`, `updated_at`, `user_id`) VALUES ('2012-06-01 19:25:45', 'example', '2012-06-01 19:25:45', 1)
如您所見,兩者都是在保存新用戶的同時保存的。 現在讓我們嘗試場景二:
u = User.create!(:name => "test")
#SQL (0.2ms) INSERT INTO `users` (`created_at`, `name`, `updated_at`) VALUES ('2012-06-01 19:27:21', 'test', '2012-06-01 19:27:21')
#<User id: 2, name: "test", created_at: "2012-06-01 19:27:21", updated_at: "2012-06-01 19:27:21">
u.assignments.build(:name => "example")
#<Assignment id: nil, name: "example", user_id: 2, created_at: nil, updated_at: nil>
因此,我們可以得出結論:
如果我執行some_user.assignments.build,是否保存了Assignment對象?
不
如果我執行some_user.assignments << Assignment.new,是否保存了Assignment對象?
不。這正是assignments.build所做的,沒有區別。
如果我做some_user.assignments << Assignment.create,是兩個數據庫調用,還是只有一個?
只是作業。
如果我在創建它之間修改Assignment對象並將其添加到some_user.assignments呢?
不明白,抱歉。
如果我保存會怎么樣! 一個Assignment對象,其相應的User尚未保存在數據庫中?
它在沒有user_id的情況下保存到數據庫中。 然后,當您為用戶調用save時,會向該分配發出更新命令以添加用戶ID。 這是在控制台:
u = User.new(:name => "John Doe")
#<User id: nil, name: "John Doe", created_at: nil, updated_at: nil>
a = Assignment.new(:name => "test")
#<Assignment id: nil, name: "test", user_id: nil, created_at: nil, updated_at: nil>
u.assignments << a
#[#<Assignment id: nil, name: "test", user_id: nil, created_at: nil, updated_at: nil>]
a.save!
#SQL (0.2ms) INSERT INTO `assignments` (`created_at`, `name`, `updated_at`, `user_id`) VALUES ('2012-06-01 19:33:24', 'test', '2012-06-01 19:33:24', NULL)
a.user_id
#nil
u.save!
#INSERT INTO `users` (`created_at`, `name`, `updated_at`) VALUES ('2012-06-01 19:33:36', 'John Doe', '2012-06-01 19:33:36')
#UPDATE `assignments` SET `user_id` = 3, `updated_at` = '2012-06-01 19:33:36' WHERE `assignments`.`id` = 3
希望這可以幫助。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.