将多级嵌套表单标记为“脏".在Rails中 [英] Marking multi-level nested forms as "dirty" in Rails

查看:71
本文介绍了将多级嵌套表单标记为“脏".在Rails中的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我在Rails中有一个三层的多嵌套表单.设置是这样的:项目有很多里程碑,而里程碑有很多注释.我们的目标是使用JavaScript在页面中进行所有内容的编辑,我们可以在页面中的项目中添加多个新的里程碑,并在新的和现有的里程碑中添加新的Notes.

I have a three-level multi-nested form in Rails. The setup is like this: Projects have many Milestones, and Milestones have many Notes. The goal is to have everything editable within the page with JavaScript, where we can add multiple new Milestones to a Project within the page, and add new Notes to new and existing Milestones.

一切正常,除了将新注释添加到现有里程碑(将新注释添加到它们时,新里程碑工作正常)之外,除非我编辑了以下任何一项,否则不会保存新注释实际属于里程碑的字段,以标记为脏"/已编辑形式.

Everything works as expected, except that when I add new notes to an existing Milestone (new Milestones work fine when adding notes to them), the new notes won't save unless I edit any of the fields that actually belong to the Milestone to mark the form "dirty"/edited.

是否可以标记里程碑,以便保存已添加的新便笺?

Is there a way to flag the Milestone so that the new Notes that have been added will save?

对不起,由于有很多部分,因此很难粘贴所有代码,但是这里有:

sorry, it's hard to paste in all of the code because there's so many parts, but here goes:

模型

class Project < ActiveRecord::Base
  has_many :notes, :dependent => :destroy
  has_many :milestones, :dependent => :destroy

  accepts_nested_attributes_for :milestones, :allow_destroy => true
  accepts_nested_attributes_for :notes, :allow_destroy => true, :reject_if => proc { |attributes| attributes['content'].blank? }
end

class Milestone < ActiveRecord::Base
  belongs_to :project
  has_many :notes, :dependent => :destroy

  accepts_nested_attributes_for :notes, :allow_destroy => true, :allow_destroy => true, :reject_if => proc { |attributes| attributes['content'].blank? }
end

class Note < ActiveRecord::Base
  belongs_to :milestone
  belongs_to :project

  scope :newest, lambda { |*args| order('created_at DESC').limit(*args.first || 3) }
end

我正在使用基于jQuery的Ryan Bates组合助手/JS代码的简单版本来完成此操作.

I'm using an jQuery-based, unobtrusive version of Ryan Bates' combo helper/JS code to get this done.

应用程序帮助程序

def add_fields_for_association(f, association, partial)
  new_object = f.object.class.reflect_on_association(association).klass.new
  fields = f.fields_for(association, new_object, :child_index => "new_#{association}") do |builder|
    render(partial, :f => builder)
  end
end

我在一个隐藏的div中呈现该关联的表单,然后使用以下JavaScript查找并根据需要添加它.

I render the form for the association in a hidden div, and then use the following JavaScript to find it and add it as needed.

JavaScript

function addFields(link, association, content, func) {
    var newID = new Date().getTime();
    var regexp = new RegExp("new_" + association, "g");
    var form = content.replace(regexp, newID);
    var link = $(link).parent().next().before(form).prev();
    if (func) {
        func.call();
    }
    return link;
}

我猜我唯一能想到的其他相关代码段就是NotesController中的create方法:

I'm guessing the only other relevant piece of code that I can think of would be the create method in the NotesController:

def create
  respond_with(@note = @owner.notes.create(params[:note])) do |format|
    format.js   { render :json => @owner.notes.newest(3).all.to_json }
    format.html { redirect_to((@milestone ? [@project, @milestone, @note] : [@project, @note]), :notice => 'Note was successfully created.') }
  end
end

@owner ivar是在以下过滤器之前创建的:

The @owner ivar is created in the following before filter:

def load_milestone
  @milestone = @project.milestones.find(params[:milestone_id]) if params[:milestone_id]
end

def determine_owner
  @owner = load_milestone || @project
end

事实是,所有这些似乎都可以正常运行,除非我要在现有里程碑中添加新注释.为了保存新笔记,必须触摸"里程碑,否则Rails不会关注.

Thing is, all this seems to work fine, except when I'm adding new notes to existing milestones. The milestone has to be "touched" in order for new notes to save, or else Rails won't pay attention.

推荐答案

这是已修复在Rails 2.3.8中.

This is bug #4242 in Rails 2.3.5 and it has been fixed in Rails 2.3.8.

这篇关于将多级嵌套表单标记为“脏".在Rails中的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆