[英]Updating a has_many :through association with a rails form
I'm trying to update the form for a Song model that has multiple Genres through a song_genre_relationships model. 我正在尝试通过song_genre_relationships模型为具有多个流派的Song模型更新表单。 I'd prefer to update the genre id's for any given song through an array in the form field. 我更愿意通过form字段中的数组更新任何给定歌曲的流派ID。
I suspect my controller is off, but I'm still pretty new to Rails and am unsure. 我怀疑我的控制器已关闭,但是我对Rails还是很陌生,并且不确定。
Here are my models, form and controller. 这是我的模型,表格和控制器。
EDITED BASED ON meagar's RESPONSE BELOW. 根据以下meagar的响应进行编辑。
song.rb song.rb
class Song < ActiveRecord::Base
has_many :song_genre_relationships
has_many :genres, :through => :song_genre_relationships
end
song_genre_relationships.rb song_genre_relationships.rb
class SongGenreRelationship < ActiveRecord::Base
belongs_to :song
belongs_to :genre
end
genre.rb 体裁
class Genre < ActiveRecord::Base
has_many :song_genre_relationships
has_many :songs, :through => :song_genre_relationships
end
song_controller.rb song_controller.rb
class SongController < ApplicationController
def update
@song = Song.find(params[:id])
relationships = @song.song_genre_relationships
@genres = Genre.all
@genres.each do |genre|
unless relationships.detect { |g| g.genre_id == genre.id }
relationships.build genre_id: genre.id
end
end
if @song.update_attributes(song_params)
flash[:notice] = "Song updated successfully."
redirect_to(:action => 'index')
else
render('edit')
end
end
private
def song_params
params.require(:song).permit(:name, :genre_ids => [])
end
_form.html.erb (song form) _form.html.erb(歌曲形式)
<%= form_for(@song) do |f| %>
<%= f.label :name, 'Title' %>
<%= f.text_field :name %>
<%= f.label :genre_ids, 'Genres' %>
<%= f.text_area :genre_ids %>
<%= f.submit %>
<% end %>
This is wrong: 这是错误的:
@genres = params[:song][:genre_ids]
Array(@genres).each do |genre|
unless relationships.detect { |g| g.genre_id == genre.id }
relationships.build genre_id: genre
end
end
params[:song][:genre_ids]
is a string. params[:song][:genre_ids]
是一个字符串。 It contains, in your example, "[<whatever id's input to the form>]"
. 在您的示例中,它包含"[<whatever id's input to the form>]"
。
You're wrapping it in an array with Array(@genres)
. 您使用Array(@genres)
将其包装在一个数组中。 Now, you have an array containing a single item, which is the string. 现在,您有一个包含单个项目(即字符串)的数组。 Then you iterate over that single item, placing it into genre
inside the loop 然后,您遍历该单个项目,并将其放入循环内的genre
Then you test g.genre_id == genre.id
. 然后测试g.genre_id == genre.id
。 genre
is that string, and you're invoking .id
on it, hence your error. genre
是该字符串,并且您正在对其调用.id
,因此会出现错误。
It's impossible to tell what you're trying to do, but you definitely cannot invoke .id
on a string and expect to get the ID of some database record back. 无法说出您要执行的操作,但是您绝对不能在字符串上调用.id
并期望获得一些数据库记录的ID。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.