Подтвердить что ты не робот

Rails fields_for: описание опции child_index

Я пытаюсь создать сложную форму со множеством вложенных моделей и сделать ее динамичной. Теперь я обнаружил, что создание вложенной модели не сложно с accepts_nested_attributes_for, но делает ее вложенной и динамической, казалось бы, невозможной, если было несколько вложенных моделей.

Я наткнулся на http://github.com/ryanb/complex-form-examples/blob/master/app/helpers/application_helper.rb, который делает это очень элегантно. Может ли кто-нибудь пролить свет на строки 13 и 16?

13 form_builder.object.class.reflect_on_association(method).klass.new

и

16 form_builder.fields_for(method, options[:object], :child_index => "new_#{method}") do |f|

Из интуиции строка 13 создает экземпляр нового объекта, но почему он должен делать так много вызовов методов? Я не мог найти документацию для опции: child_index в строке 16. Когда форма создается, очень большое число используется как индекс для новых моделей, тогда как существующие модели индексируются по их идентификатору. Как это работает?

4b9b3361

Ответ 1

options[:object] ||= form_builder.object.class.reflect_on_association(method).klass.new

Если объект не передается как параметр, он создает новый объект соответствующего класса.

form_builder.object получает главный объект из формы (project)

form_builder.object.class получает свой класс (project)

method - это имя ассоциации для проекта (:tasks)

reflect_on_association (method) дает AssociationReflection объект.

reflection_on_association (метод). klass возвращает класс ассоциации. (Task)

И, наконец, klass.new создает новый экземпляр (Task.new = > новая задача)

Это делается так, потому что имя ассоциации не всегда является просто плюрализованным именем класса, как в этом случае (Task -: tasks), но необходимо, чтобы объект класса создавал новый экземпляр.

form_builder.fields_for(method, options[:object], :child_index => "new_#{method}") do |f|
Параметр

:child_index позволяет указать индекс конкретного объекта:

project[tasks_attributes][:child_index][field_name]

Он установлен в ` "new _ # {method}" Rails, но затем заменяется на javascript (application.js):

function insert_fields(link, method, content) {
  var new_id = new Date().getTime();
  var regexp = new RegExp("new_" + method, "g")
  $(link).up().insert({
    before: content.replace(regexp, new_id)
  });
}

Указатель установлен на большое количество, просто не конфликтуя с существующими элементами. Они не индексируются id, кстати, всего от 0 до count-1