在Rails中,如何创建使用accepts_nested_attributes_for嵌套的对象?(

2019-07-30 18:28发布

在我的Rails应用程序,我试图建立创建形式为TrainingClass模型。 我想这种形式允许用户创建多个ClassMeeting模型(具有与一个belongs_to的关系TrainingClass模式)相同的形式之内,我使用accepts_nested_attributes_for做到这一点。 不幸的是,每当我提交表单我得到的错误信息: Meetings class can't be blank

我知道这是因为ClassMeeting具有validates :class_id, presence: true ,因为TrainingClass不能有一个ID,直到它被保存后,但我不知道以正确的方式来解决这个问题。 (我能想到的几个可能的方式,但它们并不完全优雅的解决方案。)任何想法? 我会很感激任何帮助,您可以给我。

注:我知道类似这样的已经过去问了不少问题。 然而,大多数的这些问题都是老有过时的答案,他们没有解决我的问题。


这里是我的代码。 请记住,虽然我已经简化为简洁它的某些方面,之间的关系ClassMeetingTrainingClass模型中保持不变:

ClassMeeting型号:

# == Schema Information
#
# Table name: class_meetings
#
#  id         :integer         not null, primary key
#  class_id   :integer
#  start      :datetime
#  end        :datetime
#  location   :string(255)
#  created_at :datetime        not null
#  updated_at :datetime        not null
#

class ClassMeeting < ActiveRecord::Base
  attr_accessible :start, :end, :location

  validates :class_id, presence: true
  validates :start, presence: true
  validates :end, presence: true
  validates :location, presence: true, length: {maximum: 255}

  belongs_to :training_class, foreign_key: :class_id, inverse_of: :meetings
end

TrainingClass型号:

# == Schema Information
#
# Table name: training_classes
#
#  id            :integer         not null, primary key
#  description   :string(255)
#  created_at    :datetime        not null
#  updated_at    :datetime        not null
#

class TrainingClass < ActiveRecord::Base
  attr_accessible :description, :meetings_attributes

  validates :description, length: {maximum: 255}

  has_many :meetings, class_name: :ClassMeeting, foreign_key: :class_id, inverse_of: :training_class

  accepts_nested_attributes_for :meetings, allow_destroy: true
end

TrainingClasses控制器:

class TrainingClassesController < ApplicationController
  def new
    @training_class = TrainingClass.new()
    @training_class.meetings.build
  end

  def create
    @training_class = TrainingClass.new()

    if @training_class.update_attributes(params[:training_class])
        redirect_to @training_class, notice: 'Class was successfully created.'
    else
        render "new"
    end
  end
end

TrainingClass表(视图):

<%= form_for @training_class do |f| %>
    <%= render 'shared/error_messages', object: f.object %>

    <%= f.text_area :description %>

    <h2>Schedule</h2>
    <%= f.fields_for :meetings do |meeting| %>
        <%= meeting.label :start, "Start of Meeting:" %>
        <%= meeting.text_field :start %>

        <%= meeting.label :end, "End of Meeting:" %>
        <%= meeting.text_field :end %>

        <%= meeting.label :location, "Location:" %>
        <%= meeting.text_field :location %>
    <% end %>

    <%= f.submit class:"btn btn-large btn-primary" %>
<% end %>

Answer 1:

好吧,我找到了解决我的问题。 所有我需要做的是验证training_class的存在,而不是在类标识码的ClassMeeting模型。 这样一个培训班的存在仍然是有效的,但验证不干扰accepts_nested_attributes_for保存模型的方法:

class ClassMeeting < ActiveRecord::Base
  attr_accessible :start, :end, :location

  validates :training_class, presence: true # :training_class instead of :class_id
  validates :start, presence: true
  validates :end, presence: true
  validates :location, presence: true, length: {maximum: 255}

  belongs_to :training_class, foreign_key: :class_id, inverse_of: :meetings
end


Answer 2:

我凝视着这个例子,尝试用我的代码不同,但最终我的问题是固定的使用:inverse_of

见accepts_nested_attributes_for子关联验证失败



文章来源: In Rails, how do I create nested objects using accepts_nested_attributes_for?