I have a User
model which has_one :profile
, and the profile
model has a type
column for Single Table Inheritance. I want a user to set type
upon signing up, and I'm having trouble doing this.
i'm trying this in my profiles controller:
def create
@profile = Profile.find(params[:id])
type = params[:user][:profile_attributes][:type]
if type && ["Artist","Listener"].include?(type)
@profile.update_attribute(:type,type)
end
end
and this in my form for the User
new view:
<%= form_for(setup_user(@user)) do |f| %>
...
<%= f.fields_for :profile do |t| %>
<div class ="field">
<%= t.label :type, "Are you an artist or listener?" %><br />
<p> Artist: <%= t.radio_button :type, "Artist" %></p>
<p> Listener: <%= t.radio_button :type, "Listener" %></p>
</div>
<% end %>
...
<% end %>
and in my application helper:
def setup_user(user)
user.tap do |u|
u.build_profile if u.profile.nil?
end
end
I can't seem to get type
set when a User is created. It still defaults to nil
. Why is this and how can I accomplish it? I'd appreciate a code example.
UPDATE:
This is 开发者_运维知识库the relevant code in my User
model:
has_one :profile
accepts_nested_attributes_for :profile
before_create :build_profile
UPDATE 2: I get this error: WARNING: Can't mass-assign protected attributes: type
It looks like the object isn't being saved to the database. Try something like this:
def create
@profile = Profile.find(params[:id])
type = params[:user][:profile_attributes][:type]
if type && ["Artist","Listener"].include?(type)
@profile.update_attribute(:type,type)
end
end
Your last issue can be resolved by adding
attr_accessible :type
"type" is a protected attribute and you can't mass-assign a protected attribute.
The column 'type' is reserved for storing the class in case of inheritance. Try renaming the table column to something like "modelname_type".
Replace your create method with this one:
def create
profile_type = params[:user][:profile][:type].constantize
if ["Artist", "Listener"].include? profile_type
@profile = current_user.profile = profile_type.new
current_user.save!
else
flash[:alert] = "Profile type not supported"
end
end
UPDATE: This is not really necessary. Useful code perhaps, but not necessary as a solution for the above problem.
精彩评论