Tyl*_*itt 5 forms ruby-on-rails
我正在我的rails应用程序中设置嵌入式表单.
这不起作用
<h1>PlayersToTeams#edit</h1>
<%= form_for @players_to_teams do |field| %>
<%= field.fields_for @players_to_teams.player do |f| %>
<%= f.label :IsActive %>
<%= f.text_field :IsActive %>
<% end %>
<%= field.label :BT %>
<%= field.text_field :BT %>
<br/>
<%= field.submit "Save", class: 'btn btn-primary' %>
<% end %>
Run Code Online (Sandbox Code Playgroud)
给我一个ActiveRecord::AssociationTypeMismatch
错误.注意@players_to_teams.player
在forms_for
行.
这确实有效:
<h1>PlayersToTeams#edit</h1>
<%= form_for @players_to_teams do |field| %>
<%= field.fields_for :player do |f| %>
<%= f.label :IsActive %>
<%= f.text_field :IsActive %>
<% end %>
<%= field.label :BT %>
<%= field.text_field :BT %>
<br/>
<%= field.submit "Save", class: 'btn btn-primary' %>
<% end %>
Run Code Online (Sandbox Code Playgroud)
注意线路中的:player
呼叫fields_for
.
什么是使用符号和使用实例之间的区别?我想我会想在这种情况下使用一个实例,但我猜不是吗?
编辑
楷模:
class Player < ActiveRecord::Base
has_many :players_to_teams
has_many :teams, through: :players_to_teams
end
class PlayersToTeam < ActiveRecord::Base
belongs_to :player
belongs_to :team
accepts_nested_attributes_for :player
end
Run Code Online (Sandbox Code Playgroud)
控制器:
class PlayersToTeamsController < ApplicationController
def edit
@players_to_teams=PlayersToTeam.find(params[:id])
end
def update
@players_to_teams=PlayersToTeam.find(params[:id])
respond_to do |format|
if @players_to_teams.update_attributes(params[:players_to_team])
format.html { redirect_to @players_to_teams, notice: 'Player_to_Team was successfully updated.' }
format.json { head :no_content }
else
format.html { render action: "edit" }
format.json { render json: @players_to_teams.errors, status: :unprocessable_entity }
end
end
end
end
Run Code Online (Sandbox Code Playgroud)
示例项目
似乎fields_for
无法弄清楚实例变量的player
关联是什么@players_to_teams
.您可以通过显式指定关联的名称(即,:player
)来绕过它.您是否在两个方向定义关联?即:
class PlayersToTeam < ActiveRecord::Base
has_one :player
end
class Player < ActiveRecord::Base
belongs_to :players_to_team
end
Run Code Online (Sandbox Code Playgroud)
另外,查看文档fields_for
,调用第一个参数record_name
,因此看起来Rails期望关联的名称而不是关联本身.但是如果不进一步研究代码,很难确切知道该方法的作用,并且他们的一些示例确实将关联直接传递给了fields_for
.
好的,我能够克隆你的示例项目并重现错误.我想我明白发生了什么.
在您调用之后accepts_nested_attributes_for
,您现在在模型上有一个名为的实例方法player_attributes=
.这是player=
通常为has_one
关联定义的方法的补充.该player_attributes=
方法接受属性的散列,而该player=
方法仅接受实际的Player
对象.
这是您调用时生成的文本输入的示例fields_for @players_to_teams.player
:
<input name="players_to_team[player][name]" ... />
Run Code Online (Sandbox Code Playgroud)
这是调用时的相同输入fields_for :player
:
<input name="players_to_team[player_attributes][name]" ... />
Run Code Online (Sandbox Code Playgroud)
当您update_attributes
在控制器中呼叫时,第一个示例将调用player=
,而第二个示例将调用player_attributes=
.在这两种情况下,传递给方法的参数都是哈希(因为params
最终只是哈希的哈希).
这就是为什么你得到一个AssociationTypeMismatch
:你不能传递一个哈希player=
,只有一个Player
对象.
看来,使用唯一安全的方式fields_for
使用accepts_nested_attributes_for
是经过协会的名称,而不是协会本身.
所以回答你原来的问题,区别在于一个有效,另一个没有:-)
归档时间: |
|
查看次数: |
1127 次 |
最近记录: |