Кто-нибудь знает, как сохранить много объектов в одной форме? - PullRequest
1 голос
/ 19 октября 2010

Я пытаюсь сохранить множество новых объектов в форме в одном ранее существовавшем родительском объекте.

- form_for :parent_object do |f|

Это начало моей формы. И тогда внутри него я бы сделал:

  - 2.times do
    - fields_for :child_object do |f|

Теперь, если бы я сохранил это, он выглядел бы как ParentObject_Controller Действие обновления, которое было бы неудачным, потому что обновление не идентифицирует новые объекты.

Так что, если бы я хотел отобразить соответствующее действие Сохранить, мне нужно было бы настроить его следующим образом:

- form_for [@parent_object, @child_object] do |f|
  - 2.times do
    - fields_for :child_object do |f|

Эта форма затем отображает действие Сохранить, но только сохраняет последний дочерний объект.

Я бы показал вам мой контроллер, но вряд ли в этом есть смысл, потому что он ужасно ошибочен.

У меня вопрос, как бы вы сохранили множество новых объектов в форме в один ранее существовавший родительский объект?

Я много смотрел на работу Райана Бэйта и много других блогов и ТАКИХ постов по этому поводу. Кажется, ничто не указывает на конкретное создание новых дочерних объектов для одного ранее существующего родительского объекта.

Обновление:

У меня сложилось впечатление, что я должен переключить действия контроллера parent_object для def update.

  elsif params[:parent_object][:child_object]
    @child_object = Child_Object.new(params[:child_object])
    if @child_object.valid? && @parent_object.referrals << @child_object
      redirect_to new_parent_object_child_object_path(@parent_object)
    else
      render :action => :new
    end

В отладчике, если я помещаю отладчик в корень def update, и я пишу:

>> params[:parent_object]
#=> nil

Интересно! Это означает, что когда child_object отправляется в контроллер parent_object, параметры для него не заполняются. Хаха, не знаю, что с этим делать ..

К сожалению, этот код не работает, это была просто моя попытка приблизиться. ;)

Ответы [ 2 ]

1 голос
/ 19 октября 2010

ОК, давайте сделаем еще один выстрел.Код взят из скринкаста РБ с замененными именами объектов:

<% form_for @parent_object do |f| %>  
  <%= f.error_messages %>  
  <!-- some field of parent object here -->
  <p>  
    <%= f.label :name %><br />  
    <%= f.text_field :name %>  
  </p>  
  <% f.fields_for :child_objects do |builder| %>  
  <!-- some fields for child objects -->
  <p>  
    <%= builder.label :content, "Some content for child object" %><br />  
    <%= builder.text_area :content, :rows => 3 %>  
    <%= builder.check_box :_destroy %>  
    <%= builder.label :_destroy, "Remove child object" %>  
  </p>  
  <% end %>  
  <p><%= f.submit "Submit" %></p>  
<% end %>

Это форма для @parent_object, которая имеет поля для :child_objects.Конечно, вы должны заменить поля своими собственными.

Чтобы это работало, вам придется создавать дочерние объекты в конструкторе:

def new  
  @parent_object = ParentObject.new  
  3.times { @parent_object.child_objects.build }  
end 

Аналогично в edit метод, который вы бы сделали:

def edit  
  @parent_object = ParentObject.find(params[:id])
  3.times { @parent_object.child_objects.build }  
end

Чтобы он работал, вам нужно определить вложенные атрибуты для дочернего объекта:

class ParentObject < ActiveRecord::Base  
  has_many :child_objects, :dependent => :destroy  
  accepts_nested_attributes_for :child_objects
end    

Надеюсь, это поможет - это именно то, чтоРБ предлагает в своих скринкастах.Дайте мне знать в комментариях, если вам нужно дополнительное объяснение.

- РЕДАКТИРОВАТЬ -

Метод обновления в parent_object_controller.rb является стандартным:

def update
  @parent_object = ParentObject.find(params[:id])
  if @parent_object.update_attributes(params[:parent_object])
    flash[:notice] = "Successfully updated parent object."
    redirect_to @parent_object
  else
    render :action => 'edit'
  end
end

Но благодаря accepts_nested_attributes_for в ParentObject будут также созданы вложенные экземпляры.

Я не включил в этот ответ весь код модели и контроллера.Вы можете увидеть оставшуюся часть кода, загрузив исходный код для этого эпизода с github.

0 голосов
/ 19 октября 2010

Вы можете взглянуть на этот ответ Я задал похожий вопрос.Есть два варианта: с отдельными формами или с одной формой.

Вам просто нужно изменить moderate_names_path на правильный путь к экземпляру вашей родительской модели (и, конечно, набор полейВы хотите изменить).Вы можете сделать это с помощью polymorphic_path :

polymorphic_path([@parent_object, @child_object])
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...