使用带有has_one关联的复选框的构建的Rails

时间:2015-06-05 01:49:38

标签: ruby-on-rails ruby-on-rails-3 has-one

我的用户是has_one个人资料,但并非所有用户都需要个人资料。我只是在用户表单上选中一个复选框(通过更新或创建)时才寻找创建配置文件的方法。

我的模特看起来像这样 -

class User < ActiveRecord::Base
has_one :profile
accepts_nested_attributes_for :profile

class Profile < ActiveRecord::Base    
belongs_to :user

理想情况下,在我的用户表单中,我想要包含一个复选框,如果选中此选项,则会创建配置文件并将配置文件中的user_id设置为相应的用户ID。

我知道在我的用户控制器中,正在进行

@user.build_profile

将在更新时创建配置文件,但不是所有用户都需要创建配置文件。

2 个答案:

答案 0 :(得分:0)

在表单中设置一个复选框,但不使用form_for符号'f'。不要使用check_box_tag

check_box_tag :create_profile

现在在创建/更新功能中,如果选中此框,则创建配置文件

@user.build_profile  if params[:create_profile]

答案 1 :(得分:0)

我尝试了类似的东西(使用Rails 4.2.4)并得出了这个解决方案。

应用/模型/ user.rb

allow_destroy: true将允许您通过用户表单销毁个人资料关联(更多here)。

class User < ActiveRecord::Base
has_one :profile
accepts_nested_attributes_for :profile, allow_destroy: true

应用/控制器/ users_controller.rb

您需要构建用户的关联配置文件实例(在newedit方法中),以便在相应的表单中正常工作。

编辑用户时,可能已存在配置文件关联。 edit方法将使用关联的配置文件(如果它存在(使用其值设置表单))或创建新的配置文件实例(如果不存在)。

另请注意,user_params包含profile_attributes: [:_destroy, :id],它将是复选框发送的值。

def new
  @user = User.new
  @user.build_profile
end

def create
  @user = User.new(user_params)
  if @user.save
    redirect_to root_path
  else
    render :new
  end
end

def edit
  @user.profile || @user.build_profile
end

def update
  if @user.update(user_params)
    redirect_to @user
  else
    render :edit
  end
end

  private

  def user_params
    params.require(:user).permit(:name, profile_attributes: [:_destroy, :id])
  end

app / views / users / new.html.rb app / views / users / edit.html.rb

使用表单中的fields_for方法提交关联数据(有关嵌套属性的更多信息,特别是一对一关系,here)。

使用复选框destroy属性创建/销毁关联的配置文件。花括号内的checked属性的值设置复选框的默认状态,具体取决于关联是否存在(更多在“更复杂的关系”标题here下)。后面的'0''1'会反转destroy方法(例如,如果选中复选框则创建关联,否则删除)(更多here)。

<%= form_for @user do |user| %>

  <%= user.fields_for :profile do |profile| %>
    <div class='form-item'>
      <%= profile.check_box :_destroy, { checked: profile.object.persisted? }, '0', '1' %>
      <%= profile.label :_destroy, 'Profile', class: 'checkbox' %>
    </div>
  <% end %>

  <%= user.submit 'Submit', class: 'button' %>

<% end %>

您可以从配置文件模型中删除主键id,因为在这种情况下它是不必要的,而link在这方面非常有用。