I was recently working on a Rails app that has a form with a parent item and child items on the same form. Ryan Bates'
complex form examples is a good place to start with this. That code will give you a simple form setup with some Javascript for adding and removing rows of children.
It works pretty well, except that in my case, I needed to ensure that each parent had a minimum of one child. I had a validation which checked for this, but it only worked for creating new records. If I removed all the child rows during an edit, the form would still save successfully. It turns out that the key is in the Rails documentation:
"Note that the model will not be destroyed until the parent is saved." So my validation was still happily finding a child row, even though it was set to be deleted. It took me some time before I found the right way to check for this, but the
marked_for_destruction? method seems to do the trick. Here's my code:
class Project < ActiveRecord::Base
has_many :tasks
accepts_nested_attributes_for :tasks, :reject_if => :all_blank, :allow_destroy => true
def validate
# require a minimum of one task
undestroyed_task_count = 0
tasks.each { |t| undestroyed_task_count += 1 unless t.marked_for_destruction? }
errors.add_to_base 'There must be at least one task' if undestroyed_task_count < 1
end
end
Hope this helps someone!