accepts_nested_attributes_for + belongs_to不显示字段

时间:2011-10-08 01:05:23

标签: ruby-on-rails-3 activerecord nested-attributes

我有两种模式:

class User < ActiveRecord::Base
  acts_as_authentic
  has_many :orders
end

class Order < ActiveRecord::Base
  belongs_to :user
  accepts_nested_attributes_for :user
end

这个想法是,如果用户已经登录,我只想为该用户订购,但如果他没有登录,那么我会要求他在订购的同时注册。 这是订单的表格

<%= form_for(@order) do |f| %>
  <div class="field">
    <%= f.label :quantity %><br />
    <%= f.number_field :quantity %>
  </div>

  <% if current_user %>
  <div class="field">
    <%= current_user.email%>
  </div>
  <%else%>
    <%= f.fields_for(:user) do |user_form| %>
        <%= render "newuser_fields", :f => user_form %>
    <% end %>
  <% end %>
  <div class="actions">
    <%= f.submit %>
  </div>
<% end %>

和新用户字段是:

<div class="field">
  <%= f.label :email %><br />
  <%= f.text_field :email %>
</div>
<div class="field">
  <%= f.label :password %><br />
  <%= f.password_field :password %>
</div>
<div class="field">
  <%= f.label :password_confirmation %><br />
  <%= f.password_field :password_confirmation %>
</div>

问题是它不会为用户显示字段!

有什么建议吗?

2 个答案:

答案 0 :(得分:2)

用户有很多订单,因此accepts_nested_attributes_for将在用户模型中使用。

http://api.rubyonrails.org/classes/ActiveRecord/NestedAttributes/ClassMethods.html

如果父项不存在,则无法保存嵌套资源,因此您将首先创建用户,然后创建其订单。

通常,如果user不存在,则会重定向到注册页面。如果您不想这样做,您可以在OrderController#new行动中执行类似的操作

if current_user
  @order=current_user.orders.build
else
  @user=User.new
end

在您的订单中,您可以检查用户是否只是创建订单表单,如果没有创建用户表单,然后添加嵌套归档订单

# app/views/order/_form.html.erb
<% if user_signed_in? %>
  //order form

<% else %>
  // user form 
  <% form_for @user do |uf| %>
    <%= uf.text_filed :email %>
    <%= uf.password_filed :password %>
    //now order fileds
    <%= uf.fields_for :orders do |of| %>
      //porder fileds 
    <% end %>
  <% end %>
<% end %>

然后在create针对用户和订单的操作中,您必须添加适当的检查

这是一个黑客,展示了如何将accepts_nested_attributes_forbelongs_to一起使用:

accepts_nested_attributes_for with belongs_to polymorphic

答案 1 :(得分:2)

或者你可以不使用accepts_nested_attributes(并且仍然使用fields_for)。用户数据将在params [:user](或params [:order] [:user]或params [:users]中,不确定,只需查看服务器日志,删除accepts_nested_attributes之后,因为这将更改字段名称)。因此,您可以先在控制器创建操作中手动创建用户:

@user = current_user || User.create!(params[:user])
@order = @user.orders.build(params[:order])

额外的好处是你可以通过这种方式获得更多的控制权,而且只有1行更多。