Mar*_*tto 5 activerecord ruby-on-rails data-modeling relationship has-many-through
我有一个看起来像这样的Artist模型:
# app/models/artist.rb
class Artist < ActiveRecord::Base
# Relationships
has_many :releases
has_many :songs, :through => :releases
has_many :featured_songs, :through => :releases,
:class_name => "Song",
:source => :song,
:conditions => { 'releases.featured', true }
end
Run Code Online (Sandbox Code Playgroud)
检索featured_songs非常有效.这里的问题是我无法向艺术家添加新的feature_song,因为出于某种原因,'featured'属性被设置为'nil'.
这就是我正在尝试的:
ruby-1.9.2-p180 :004 > a = Artist.first
ruby-1.9.2-p180 :005 > a.featured_songs.create(:title => "Title", :user => User.first)
Run Code Online (Sandbox Code Playgroud)
实际结果是:
ruby-1.9.2-p180 :004 > a = Artist.first
ruby-1.9.2-p180 :005 > a.featured_songs.create(:title => "Title", :user => User.first)
User Load (0.9ms) SELECT `users`.* FROM `users` LIMIT 1
SQL (1.0ms) BEGIN
SQL (5.5ms) INSERT INTO `songs` (`created_at`, `title`, `updated_at`, `user_id`) VALUES (?, ?, ?, ?) [["created_at", Thu, 11 Aug 2011 18:30:34 UTC +00:00], ["title", "Title"], ["updated_at", Thu, 11 Aug 2011 18:30:34 UTC +00:00], ["user_id", 1]]
SQL (1.2ms) INSERT INTO `releases` (`album_id`, `artist_id`, `created_at`, `featured`, `song_id`, `updated_at`) VALUES (?, ?, ?, ?, ?, ?) [["album_id", nil], ["artist_id", 1], ["created_at", Thu, 11 Aug 2011 18:30:34 UTC +00:00], ["featured", nil], ["song_id", 6], ["updated_at", Thu, 11 Aug 2011 18:30:34 UTC +00:00]]
(0.1ms) COMMIT
Run Code Online (Sandbox Code Playgroud)
注意: ["featured", nil]
知道我做错了什么吗?如何在不直接访问连接的情况下正确设置连接的属性?
谢谢!
编辑:使我的问题更清楚:
从艺术家的例子来看,我无法通过这种featured_songs关系创作新的特色歌曲
保存似乎是将所有歌曲属性设置为EXCEPT(最重要的一个) featured
该featured属性nil由于某种原因被设置为,这是真正的问题.
编辑:更新:releases_attributes 以反映 has_many 关系。
杰德尔的回答是正确的。这是一个解决的问题accepts_nested_attributes_for。has_many仅描述查询记录的机制,而不是更新或创建记录的机制。
您列出的属性被更新的原因是因为它们是歌曲对象的一部分。您尝试更新的字段是特色字段,它是releases连接表的一部分。
accepts_nested_attributes_for是解决更新嵌套关系问题的工具。如果您想在创建歌曲对象期间添加特色属性(如您在示例中所做的那样),那么您需要将其添加为 Song 类的嵌套属性的一部分。
class Song < ActiveRecord::Base
has_many :releases
has_many :artists, :through => :releases
accepts_nested_attributes_for :releases
end
Run Code Online (Sandbox Code Playgroud)
然后你create会看起来像这样:
a.songs.create(:title => 'Title', :user => User.first, :releases_attributes => [{ :id => 123, :featured => true}])
Run Code Online (Sandbox Code Playgroud)
请注意添加_attributes。如果您使用嵌套表单,这正是 Rails 在视图中执行的操作。请参阅 ActiveRecord 源文件nested_attributes.rb以获取证明。
如果您确实想要一种更简洁的方法来完成此操作,您可以添加一个Song#create_featured方法,将:releases_attributes哈希值合并到#create.
| 归档时间: |
|
| 查看次数: |
3392 次 |
| 最近记录: |