1

我有用户,它可以是三种类型之一:管理员、学生、教师。每个人都有其他属性。我正在尝试像这样一对一的多态关联:

用户

class User < ActiveRecord::Base
    belongs_to :identity, :polymorphic => true
    accepts_nested_attributes_for :identity, :allow_destroy => true

    attr_accessible :email, :login, :remember_token, 
                    :password_confirmation, :password, :role
end

学生

class Student < ActiveRecord::Base
    attr_accessible :field

    has_one :user, :as => :identity
end

控制器

def new
     @user = User.new
end
def create
    @user = User.new(params[:user]) # It fails here.
    @user.identita.build
    ...
end

看法

<%= form_for(@user) do |f| %>
    <%= f.label :login %><br />
    <%= f.text_field :login %>

    <%= f.fields_for [:identity, Student.new] do |i| %>  
    <%= i.label :field %><br />
    <%= i.textfield_select :field  %>
    <% end %>
<% end %>

当我提交这个视图(更复杂,但这是核心)时,它会像这样发送哈希:

{"utf8"=>"✓",
 "authenticity_token"=>"...",
 "user"=>{"login"=>"...",
 "student"=> {"field"=>"..."}
}

因此它在控制器中的标记线上失败:

ActiveModel::MassAssignmentSecurity::Error in UsersController#create
Can't mass-assign protected attributes: student

我究竟做错了什么?像 :as=>"student" 或扭曲现实?

4

2 回答 2

4

首先,修复:

<%= f.fields_for [:identity, Student.new] do |i| %>  

至:

<%= f.fields_for :identity, Student.new do |i| %>

其次,你正试图accepts_nested_attributes_for在一段belongs_to关系中使用。这是不支持的行为 AFAIK。也许尝试将其移至Student模型:

class Student < ActiveRecord::Base
  attr_accessible :field

  has_one :user, :as => :identity
  accepts_nested_attributes_for :user, :allow_destroy => true
end

并制作这样的视图:

<%= form_for(Student.new) do |i| %>
  <%= i.fields_for :user, @user do |f| %>  
    <%= f.label :login %><br />
    <%= f.text_field :login %>
  <% end %>
  <%= i.label :field %><br />
  <%= i.textfield_select :field  %>
<% end %>
于 2012-08-09T20:19:50.127 回答
0

来自attr_accessible 的文档

attr_accessible 只会设置此列表中的属性,以分配给 您可以使用直接编写器方法的其余属性。

因此,一旦您使用attr_accessible了 ,另一个属性将自动成为受保护的属性。

于 2012-08-09T20:15:11.890 回答