代码之家  ›  专栏  ›  技术社区  ›  Chowlett

从父窗体创建一组子对象

  •  3
  • Chowlett  · 技术社区  · 16 年前

    幸亏 Ruby on Rails: How to gather values for child tables from a form? fields_for

    假设我有一个模型 Person . 有一个 name 属性,以及 has_many :foos . 这个 Foo 模型,反过来,有一个 colour

    正好三个 Foos new create PersonController ,以及 新的

    还有,我可以不做这个吗 accepts_nested_attributes_for ?

    1 回复  |  直到 9 年前
        1
  •  3
  •   Chowlett    16 年前

    在对不同位置的方括号和不同的循环进行了一些研究之后,我想我已经解决了这个问题。下面是我的代码现在的样子(根据脚手架设置路线,以便从 /new 触发 create

    models/person.rb

    class Person < ActiveRecord::Base
      has_many :foos
      validates_presence_of :name
    end
    

    模型/foo.rb

    class Foo < ActiveRecord::Base
      belongs_to :person
      validates_presence_of :colour
      validates_uniqueness_of :colour, :scope => "person_id"
    end
    

    控制器/人员\u controller.rb

    def new
      # Set up a Person with 3 defaulted Foos
      @person = Person.new
      (1..3).each { |i| @person.foos.build }
    end
    
    def create
      # Create (but don't save) a Person as specified
      @person = Person.new(params[:person])
    
      # Create (but don't save) a Foo for each set of Foo details
      @foos = []
      params[:foo].each do |foo_param|
        @foos << Foo.new(foo_param)
      end
    
      # Save everything in a transaction
      Person.transaction do
        @person.save!
        @foos.each do |foo|
          foo.person = @person
          foo.save!
        end
      end
    
      redirect_to :action => 'show', :id => @person
    
    rescue ActiveRecord::RecordInvalid => e
      @foos.each do |foo|
        foo.valid?
      end
      render :action => 'new'
    end
    

    views/people/new.html.erb

    <% form_for :person do |f| %>
      <%= error_messages_for :object => [@person] + @person.foos %>
    
      <p>
        <%= f.label :name %><br />
        <%= f.text_field :name %>
      </p>
    
      <table>
      <% @person.foos.each_with_index do |foo, index| @foo = foo%>
        <tr>
          <td><%= label :colour, "Foo colour #{index + 1}: " %></td>
          <td><%= text_field("foo[]", "colour" %></td>
        </tr>          
      <% end %>
      </table>
    
      <p>
        <%= f.submit 'Create' %>
      </p>
    <% end %>
    

    这似乎奏效了。