page.insert_html没有插入带有link_to_function(rails)的html

时间:2009-07-28 14:41:22

标签: javascript ruby-on-rails ruby

我正在尝试在Ruby On Rails中执行复杂的表单。它应该分组,每组应该有文本字段。我想要添加和删除组和文本字段。

我已经成功地添加了文本字段并将其删除,但是我完全无法对这些组进行相同操作。

这是对函数的调用:

<%= link_to_function 'Add group' do |page|
page.insert_html :bottom, :groups, :partial => 'group' 
end %>

所以,它应该将名为“group”的部分添加到“groups”div中,对吗?好吧,它没有。这是部分:

<div id="group" class='elements'>
    <p>
        <g_title>Text Group</g_title>
        <add><%= add_text_link 'Add a text field'%></add>
        <remove><%= link_to_function 'Remove text group', "this.up('.elements').remove()" %></remove>
    </p>

    <%= render :partial => 'text' %>
</div>

如果我点击“添加新组”链接,Firebug告诉我有一些错误,例如某些javascript代码无效(错误在属性列表后“丢失”)。但是,如果我删除部分代码中的第四行(具有“add_text_link”功能的那一行),它就完美了!而且这个功能很完美。

那么,任何想法?

感谢您的帮助!

编辑:这是生成的源代码:

<form action="/collect/text" method="post"><div style="margin:0;padding:0"><input name="authenticity_token" type="hidden" value="b2zqh1op9oHbjQ33mMAWEhZcEqHoYhUIMV0uPH8F2ms=" /></div>
<div id= 'main_elements' class='elements'>
    <p><g_title>Main elements</g_title></p>

    <p><input id="Title" name="Title" size="50" type="text" /> 
        <label class="h0" for="Title">Title</label> <options>(mandatory)</options></p>
    <p><input id="Subtitle" name="Subtitle" size="50" type="text" /> 
    <label class="h0" for="Subtitle">Subtitle</label> <options>(optional)</options></p>

</div>

<div id='groups' class="groups">
    <p><add><a href="#" onclick="try {
Element.insert(&quot;groups&quot;, { bottom: &quot;&lt;p&gt;&lt;/p&gt;\n&lt;div id=\&quot;group\&quot; class='elements'&gt;\n\t&lt;p&gt;\n\t\t&lt;g_title&gt;Text Group&lt;/g_title&gt;\n\t\t&lt;add&gt;&lt;a href=\&quot;#\&quot; onclick=\&quot;try {\nElement.insert(&quot;group&quot;, { bottom: &quot;\\n&lt;div class='text'&gt;\\n\\t&lt;p&gt;\\n\\t\\tText &lt;input id=\\&quot;content\\&quot; name=\\&quot;content\\&quot; size=\\&quot;50\\&quot; type=\\&quot;text\\&quot; /&gt; Importance &lt;select id=\\&quot;t1\\&quot; name=\\&quot;t1\\&quot;&gt;&lt;option value=\\&quot;notes\\&quot;&gt;Notes&lt;/option&gt;\\n&lt;option value=\\&quot;highlighted\\&quot;&gt;Highlighted text&lt;/option&gt;\\n&lt;option value=\\&quot;normal\\&quot;&gt;Normal text&lt;/option&gt;&lt;/select&gt;\\n\\t\\t&lt;remove&gt;&lt;a href=\\&quot;#\\&quot; onclick=\\&quot;this.up('.text').remove(); return false;\\&quot;&gt;Remove text field&lt;/a&gt;&lt;/remove&gt;\\n\\t&lt;/p&gt;\\n&lt;/div&gt;&quot; });\nnew Effect.Highlight(&quot;group&quot;,{duration:0.3, startcolor:'#34d85e'});\n} catch (e) { alert('RJS error:\\n\\n' + e.toString()); alert('Element.insert(\\&quot;group\\&quot;, { bottom: \\&quot;\\\\n&lt;div class=\\'text\\'&gt;\\\\n\\\\t&lt;p&gt;\\\\n\\\\t\\\\tText &lt;input id=\\\\\\&quot;content\\\\\\&quot; name=\\\\\\&quot;content\\\\\\&quot; size=\\\\\\&quot;50\\\\\\&quot; type=\\\\\\&quot;text\\\\\\&quot; /&gt; Importance &lt;select id=\\\\\\&quot;t1\\\\\\&quot; name=\\\\\\&quot;t1\\\\\\&quot;&gt;&lt;option value=\\\\\\&quot;notes\\\\\\&quot;&gt;Notes&lt;/option&gt;\\\\n&lt;option value=\\\\\\&quot;highlighted\\\\\\&quot;&gt;Highlighted text&lt;/option&gt;\\\\n&lt;option value=\\\\\\&quot;normal\\\\\\&quot;&gt;Normal text&lt;/option&gt;&lt;/select&gt;\\\\n\\\\t\\\\t&lt;remove&gt;&lt;a href=\\\\\\&quot;#\\\\\\&quot; onclick=\\\\\\&quot;this.up(\\'.text\\').remove(); return false;\\\\\\&quot;&gt;Remove text field&lt;/a&gt;&lt;/remove&gt;\\\\n\\\\t&lt;/p&gt;\\\\n&lt;/div&gt;\\&quot; });\\nnew Effect.Highlight(\\&quot;group\\&quot;,{duration:0.3, startcolor:\\'#34d85e\\'});'); throw e }; return false;\&quot;&gt;Add a text field&lt;/a&gt;&lt;/add&gt;\n\t\t&lt;remove&gt;&lt;a href=\&quot;#\&quot; onclick=\&quot;this.up('.elements').remove(); return false;\&quot;&gt;Remove text group&lt;/a&gt;&lt;/remove&gt;\n\t&lt;/p&gt;\n\t\n\t\n&lt;div class='text'&gt;\n\t&lt;p&gt;\n\t\tText &lt;input id=\&quot;content\&quot; name=\&quot;content\&quot; size=\&quot;50\&quot; type=\&quot;text\&quot; /&gt; Importance &lt;select id=\&quot;t1\&quot; name=\&quot;t1\&quot;&gt;&lt;option value=\&quot;notes\&quot;&gt;Notes&lt;/option&gt;\n&lt;option value=\&quot;highlighted\&quot;&gt;Highlighted text&lt;/option&gt;\n&lt;option value=\&quot;normal\&quot;&gt;Normal text&lt;/option&gt;&lt;/select&gt;\n\t\t&lt;remove&gt;&lt;a href=\&quot;#\&quot; onclick=\&quot;this.up('.text').remove(); return false;\&quot;&gt;Remove text field&lt;/a&gt;&lt;/remove&gt;\n\t&lt;/p&gt;\n&lt;/div&gt;\n&lt;/div&gt;&quot; });
new Effect.Highlight(&quot;group&quot;,{duration:0.3, startcolor:'#34d85e'});
} catch (e) { alert('RJS error:\n\n' + e.toString()); alert('Element.insert(\&quot;groups\&quot;, { bottom: \&quot;&lt;p&gt;&lt;/p&gt;\\n&lt;div id=\\\&quot;group\\\&quot; class=\'elements\'&gt;\\n\\t&lt;p&gt;\\n\\t\\t&lt;g_title&gt;Text Group&lt;/g_title&gt;\\n\\t\\t&lt;add&gt;&lt;a href=\\\&quot;#\\\&quot; onclick=\\\&quot;try {\\nElement.insert(&quot;group&quot;, { bottom: &quot;\\\\n&lt;div class=\'text\'&gt;\\\\n\\\\t&lt;p&gt;\\\\n\\\\t\\\\tText &lt;input id=\\\\&quot;content\\\\&quot; name=\\\\&quot;content\\\\&quot; size=\\\\&quot;50\\\\&quot; type=\\\\&quot;text\\\\&quot; /&gt; Importance &lt;select id=\\\\&quot;t1\\\\&quot; name=\\\\&quot;t1\\\\&quot;&gt;&lt;option value=\\\\&quot;notes\\\\&quot;&gt;Notes&lt;/option&gt;\\\\n&lt;option value=\\\\&quot;highlighted\\\\&quot;&gt;Highlighted text&lt;/option&gt;\\\\n&lt;option value=\\\\&quot;normal\\\\&quot;&gt;Normal text&lt;/option&gt;&lt;/select&gt;\\\\n\\\\t\\\\t&lt;remove&gt;&lt;a href=\\\\&quot;#\\\\&quot; onclick=\\\\&quot;this.up(\'.text\').remove(); return false;\\\\&quot;&gt;Remove text field&lt;/a&gt;&lt;/remove&gt;\\\\n\\\\t&lt;/p&gt;\\\\n&lt;/div&gt;&quot; });\\nnew Effect.Highlight(&quot;group&quot;,{duration:0.3, startcolor:\'#34d85e\'});\\n} catch (e) { alert(\'RJS error:\\\\n\\\\n\' + e.toString()); alert(\'Element.insert(\\\\&quot;group\\\\&quot;, { bottom: \\\\&quot;\\\\\\\\n&lt;div class=\\\\\'text\\\\\'&gt;\\\\\\\\n\\\\\\\\t&lt;p&gt;\\\\\\\\n\\\\\\\\t\\\\\\\\tText &lt;input id=\\\\\\\\\\\\&quot;content\\\\\\\\\\\\&quot; name=\\\\\\\\\\\\&quot;content\\\\\\\\\\\\&quot; size=\\\\\\\\\\\\&quot;50\\\\\\\\\\\\&quot; type=\\\\\\\\\\\\&quot;text\\\\\\\\\\\\&quot; /&gt; Importance &lt;select id=\\\\\\\\\\\\&quot;t1\\\\\\\\\\\\&quot; name=\\\\\\\\\\\\&quot;t1\\\\\\\\\\\\&quot;&gt;&lt;option value=\\\\\\\\\\\\&quot;notes\\\\\\\\\\\\&quot;&gt;Notes&lt;/option&gt;\\\\\\\\n&lt;option value=\\\\\\\\\\\\&quot;highlighted\\\\\\\\\\\\&quot;&gt;Highlighted text&lt;/option&gt;\\\\\\\\n&lt;option value=\\\\\\\\\\\\&quot;normal\\\\\\\\\\\\&quot;&gt;Normal text&lt;/option&gt;&lt;/select&gt;\\\\\\\\n\\\\\\\\t\\\\\\\\t&lt;remove&gt;&lt;a href=\\\\\\\\\\\\&quot;#\\\\\\\\\\\\&quot; onclick=\\\\\\\\\\\\&quot;this.up(\\\\\'.text\\\\\').remove(); return false;\\\\\\\\\\\\&quot;&gt;Remove text field&lt;/a&gt;&lt;/remove&gt;\\\\\\\\n\\\\\\\\t&lt;/p&gt;\\\\\\\\n&lt;/div&gt;\\\\&quot; });\\\\nnew Effect.Highlight(\\\\&quot;group\\\\&quot;,{duration:0.3, startcolor:\\\\\'#34d85e\\\\\'});\'); throw e }; return false;\\\&quot;&gt;Add a text field&lt;/a&gt;&lt;/add&gt;\\n\\t\\t&lt;remove&gt;&lt;a href=\\\&quot;#\\\&quot; onclick=\\\&quot;this.up(\'.elements\').remove(); return false;\\\&quot;&gt;Remove text group&lt;/a&gt;&lt;/remove&gt;\\n\\t&lt;/p&gt;\\n\\t\\n\\t\\n&lt;div class=\'text\'&gt;\\n\\t&lt;p&gt;\\n\\t\\tText &lt;input id=\\\&quot;content\\\&quot; name=\\\&quot;content\\\&quot; size=\\\&quot;50\\\&quot; type=\\\&quot;text\\\&quot; /&gt; Importance &lt;select id=\\\&quot;t1\\\&quot; name=\\\&quot;t1\\\&quot;&gt;&lt;option value=\\\&quot;notes\\\&quot;&gt;Notes&lt;/option&gt;\\n&lt;option value=\\\&quot;highlighted\\\&quot;&gt;Highlighted text&lt;/option&gt;\\n&lt;option value=\\\&quot;normal\\\&quot;&gt;Normal text&lt;/option&gt;&lt;/select&gt;\\n\\t\\t&lt;remove&gt;&lt;a href=\\\&quot;#\\\&quot; onclick=\\\&quot;this.up(\'.text\').remove(); return false;\\\&quot;&gt;Remove text field&lt;/a&gt;&lt;/remove&gt;\\n\\t&lt;/p&gt;\\n&lt;/div&gt;\\n&lt;/div&gt;\&quot; });\nnew Effect.Highlight(\&quot;group\&quot;,{duration:0.3, startcolor:\'#34d85e\'});'); throw e }; return false;">Add new group</a></add></p>

    <p></p>
<div id="group" class='elements'>
    <p>
        <g_title>Text Group</g_title>
        <add><a href="#" onclick="try {
Element.insert(&quot;group&quot;, { bottom: &quot;\n&lt;div class='text'&gt;\n\t&lt;p&gt;\n\t\tText &lt;input id=\&quot;content\&quot; name=\&quot;content\&quot; size=\&quot;50\&quot; type=\&quot;text\&quot; /&gt; Importance &lt;select id=\&quot;t1\&quot; name=\&quot;t1\&quot;&gt;&lt;option value=\&quot;notes\&quot;&gt;Notes&lt;/option&gt;\n&lt;option value=\&quot;highlighted\&quot;&gt;Highlighted text&lt;/option&gt;\n&lt;option value=\&quot;normal\&quot;&gt;Normal text&lt;/option&gt;&lt;/select&gt;\n\t\t&lt;remove&gt;&lt;a href=\&quot;#\&quot; onclick=\&quot;this.up('.text').remove(); return false;\&quot;&gt;Remove text field&lt;/a&gt;&lt;/remove&gt;\n\t&lt;/p&gt;\n&lt;/div&gt;&quot; });
new Effect.Highlight(&quot;group&quot;,{duration:0.3, startcolor:'#34d85e'});
} catch (e) { alert('RJS error:\n\n' + e.toString()); alert('Element.insert(\&quot;group\&quot;, { bottom: \&quot;\\n&lt;div class=\'text\'&gt;\\n\\t&lt;p&gt;\\n\\t\\tText &lt;input id=\\\&quot;content\\\&quot; name=\\\&quot;content\\\&quot; size=\\\&quot;50\\\&quot; type=\\\&quot;text\\\&quot; /&gt; Importance &lt;select id=\\\&quot;t1\\\&quot; name=\\\&quot;t1\\\&quot;&gt;&lt;option value=\\\&quot;notes\\\&quot;&gt;Notes&lt;/option&gt;\\n&lt;option value=\\\&quot;highlighted\\\&quot;&gt;Highlighted text&lt;/option&gt;\\n&lt;option value=\\\&quot;normal\\\&quot;&gt;Normal text&lt;/option&gt;&lt;/select&gt;\\n\\t\\t&lt;remove&gt;&lt;a href=\\\&quot;#\\\&quot; onclick=\\\&quot;this.up(\'.text\').remove(); return false;\\\&quot;&gt;Remove text field&lt;/a&gt;&lt;/remove&gt;\\n\\t&lt;/p&gt;\\n&lt;/div&gt;\&quot; });\nnew Effect.Highlight(\&quot;group\&quot;,{duration:0.3, startcolor:\'#34d85e\'});'); throw e }; return false;">Add a text field</a></add>
        <remove><a href="#" onclick="this.up('.elements').remove(); return false;">Remove text group</a></remove>
    </p>



<div class='text'>
    <p>
        Text <input id="content" name="content" size="50" type="text" /> Importance <select id="t1" name="t1"><option value="notes">Notes</option>
<option value="highlighted">Highlighted text</option>
<option value="normal">Normal text</option></select>
        <remove><a href="#" onclick="this.up('.text').remove(); return false;">Remove text field</a></remove>

    </p>
</div>
</div>

</div>

<div class="button">
    <p><next><a href="#" onclick="$(this).up('form').submit(); return false;">Next Step</a></next></p>
</div>
</form>

2 个答案:

答案 0 :(得分:2)

我成功完成了这项工作。在我看来,这是Rails中的一个错误,因为使用了escape_once而不是html_escape。换句话说,第一个link_to_function被转义,但第二个不是,因为该字符串已经被转义。这使得反向操作(去逃逸或其他)不起作用。您可以将此代码添加到初始化程序以始终转义:

module ActionView
  module Helpers
    module TagHelper
      private
        def tag_options(options, escape = true)
          unless options.blank?
            attrs = []
            if escape
              options.each do |key, value|
                next unless value
                key = key.to_s
                value = BOOLEAN_ATTRIBUTES.include?(key) ? key : ERB::Util::html_escape(value)
                attrs << %(#{key}="#{value}")
              end
            else
              attrs = options.map { |key, value| %(#{key}="#{value}") }
            end
            " #{attrs.sort * ' '}" unless attrs.empty?
          end
        end
    end
  end
end

此代码可能会破坏内容,因此请谨慎使用。但是,我已经读过可能在Rails 3.0中更改了escape_once,所以请保持手指交叉;)

答案 1 :(得分:0)

你做错了。这最终会在HTML属性中插入转义的部分转义和转义字符串。那简直就是邪恶。它有很多方法可以打破。

您可能想要考虑一种更简单的方法。将render :partial置于link_to_function 'Add a group'之上。隐藏div#group,然后链接到$('group').show()

换句话说,将其隐藏起来,然后使用JavaScript显示它,而不是将其插入DOM中。更简单,更不容易出错。