我有这些模特:
class User < ActiveRecord::Base
has_one :city
accepts_nested_attributes_for :city
end
class City < ActiveRecord::Base
belongs_to :user
end
此控制器操作:
def create
@user = User.new(params[:user])
respond_to do |format|
if @user.save
format.html { redirect_to(@user, :notice => 'User was successfully created.') }
format.xml { render :xml => @user, :status => :created, :location => @user }
else
format.html { render :action => "new" }
format.xml { render :xml => @user.errors, :status => :unprocessable_entity }
end
end
end
和这个观点:
<%= form_for :user,:url => users_path,:method => :post do |f| %>
<%= f.fields_for :city do |b| %>
<%= b.collection_select :id,City.all,:id,:name %>
<% end %>
<div class="field">
<%= f.label :name %><br />
<%= f.text_field :name %>
</div>
<div class="actions">
<%= f.submit %>
</div>
<% end %>
我正在尝试允许用户从已添加的城市列表中选择一个城市。我想给他一个选择。它工作的选择部分,但生成的html代码,如下所示:
<select name="user[city][id]" id="user_city_id">
<option value="1">One</option>
<option value="2">Two</option>
</select>
请注意,它的名称在任何地方都没有attribute
。所以,当我尝试保存它时,我收到了这个错误:
City(#37815120) expected, got ActiveSupport::HashWithIndifferentAccess(#32969916)
我该如何解决这个问题?
编辑:有一些进展,我试图将fields_for更改为:
<%= f.fields_for :city_attributes do |b| %>
<%= b.collection_select :id,City.all,:id,:name %>
<% end %>
现在,html似乎正确生成了。但我现在得到这个错误:
Couldn't find City with ID=1 for User with ID=
我不知道下一步该做什么。
EDIT2:覆盖city_attributes=
方法似乎有效:
def city_attributes=(attribs)
self.city = City.find(attribs[:id])
end
我不知道这是否可行,但看起来不错。
答案 0 :(得分:2)
看看这个与你的相似的问题: Rails 3: How does "accepts_nested_attributes_for" work?
实际上,由于城市已经存在,我认为这里不需要嵌套表格。
尝试替换
<%= f.fields_for :city_attributes do |b| %>
<%= b.collection_select :id,City.all,:id,:name %>
<% end %>
使用
<%= f.collection_select :city, City.all,:id,:name %>
更新后的评论
您可以更改您的关系(并相应地更新数据库方案)
class User < ActiveRecord::Base
belongs_to :city
end
class City < ActiveRecord::Base
has_many :users
end
然后尝试使用:
<%= f.collection_select :city_id, City.all,:id,:name %>
答案 1 :(得分:1)
你也可以做一个
<%= f.collection_select :city_id, City.all, :id, :name %>
,然后将虚拟属性添加到您的用户模型:
class User < ActiveRecord::Base
...
def city_id(c_id)
update_attribute(:city, City.find(c_id))
end
def city_id
city.id
end
end
这可能不是很干净,因为只要为some_user.city_id分配ID,就会“保存”关联的City模型。但是,此解决方案可以使您的控制器和视图保持良好和干净。
注意:您可能还想考虑传入setter方法的空白ID。
答案 2 :(得分:0)
试试这个
&lt;%= f.select(:city_id,City.all.collect {| p | [p.name,p.id]})%&gt;