【问题标题】:Form submitted multiple times when using the "submit" callback and $.ajax to post it使用“提交”回调和 $.ajax 发布时多次提交的表单
【发布时间】:2010-10-14 16:13:29
【问题描述】:

我一直在使用以下代码观察到一些奇怪的行为:

$.fn.submit_to_remote = function() {
  // I use .each instead of the .submit directly so I can save
  // the 'submitEnabled' variable separately for each form
  jQuery.each($(this), function() {
    $(this).submit(function() {
      form = $(this);
      if (form.data('submitEnabled') == false) { alert('disabled'); return false; }
      form.data('submitEnabled', false);
      $.ajax({type: 'POST', url: 'url', data: data, dataType: 'script',
        success: function(script) {
          alert('success')
        }
      })
      return false;
    })
  })
}
$('.submit_to_remote').submit_to_remote();

因此,基本上,在表单上调用 submit_to_remote 时,它​​将禁用正常提交,然后发出 AJAX POST 请求。

奇怪的是表单被多次发布,因为“禁用”警报会显示。如您所见,我通过使用保存在表单对象上的“变量”来防止这种情况发生,并检查该变量以查看表单是否已提交。

经过进一步测试,罪魁祸首似乎是 AJAX 调用返回的脚本。让我解释一下我在做什么,这样会更清楚。

表单被发送到服务器,并返回一个脚本。该脚本再次显示表单,但这次显示某些字段的错误消息。请注意,表单已完全替换。

脚本在显示新表单后执行:

$('.submit_to_remote').submit_to_remote();

我必须这样做,否则,当您再次单击提交按钮时,表单会正常提交,没有 AJAX。

因此,假设用户提交表单并返回相应错误(未显示“禁用”警报)。然后他再次提交;这次“禁用”警报显示一次。现在他又提交了一次,这次警报显示了两次!等等……

所以看起来每次请求都会一次又一次地附加 .submit 回调,但为什么呢?

难道是通过使用 .html() 将原始表单保留为幽灵或其他东西?

谢谢!

PS:如果相关,这里是 $.ajax 调用返回的脚本:

replace_content_with = 'the form and other stuff here';
$('.page-content').html(replace_content_with);
$('.submit_to_remote').submit_to_remote();

【问题讨论】:

    标签: jquery ajax forms


    【解决方案1】:

    是的,我同意 Seb,这是一个很好的做法,我认为在绑定之前始终取消绑定,除非您确定当前没有您想要的元素绑定。您可以通过简单地使用“.submit”、“.click”、“.mouseover”等功能来意外地双重绑定您的东西。

    养成这样做的习惯(对我来说永远不会失败):

    $('.some_element').unbind('submit').bind('submit',function() {
        // do stuff here...
    });
    

    ...而不是:

    $('.some_element').submit(function() {
        // do stuff here...
    });
    

    【讨论】:

    • 我试试这个,但在我的情况下,有表单的提交,但如果我更新表单内容并重新提交,提交会发送原始内容。如果我不这样做,我将提交增量表单(1、2、3 等...)。
    • 因为我重新绑定了提交“点击”按钮和“提交”操作,我的表单每次点击发送 4 次。讨厌的东西。完美的解决方案,但我很难量化我在寻找什么,从而找到了这个页面。
    • 谢谢,拯救我的一天! ;))
    • 这是一个很好的解决方案。谢谢,您节省了我的时间。
    • 这项工作对我来说非常棒,我会接受这个练习
    【解决方案2】:

    解除绑定对我不起作用。这样做了:

    $(document).off('submit');
    $(document).on('submit',"#element_id",function(e){
        e.preventDefault();
        //do something
    }); 
    

    希望对你有帮助……

    其实 unbind() 如果在提交前进行一些验证和返回,可能会给你带来一些麻烦。示例:

    $(document).on('submit',"#element_id",function(e){
        e.preventDefault();
        $(document).unbind('submit');
        var name = $(this).children('input[name="name"]').val();
        if( name == 'wrong name')
            return;
    
        //do something
    });
    

    在这种情况下,如果您输入的是“错误名称”,则不会提交表单,之后,当您输入“正确名称”时,不会触发 $(document).on('submit'.. , 既不是 e.preventDefault(); 也会以常规方式提交您的表单。

    【讨论】:

    • 谢谢 - 这正是我所需要的
    【解决方案3】:

    不确定这种奇怪的行为,但似乎解除对提交事件的绑定可以解决问题。

    因此,在运行 $.ajax 调用返回的脚本之前,请运行以下代码:

    $('.submit_to_remote').unbind("submit");
    

    这应该删除以前的绑定,只留下新的。

    【讨论】:

    • 我忘了说我也试过了,但奇怪的是它不起作用,因为新表单不会有 AJAX 行为,即使我用脚本重新绑定它。 ..
    • +1 我可以在这里使用它作为解决方案:stackoverflow.com/questions/12340484/…
    【解决方案4】:

    更简单的是:

    $(".some-class").off().submit(function() {
        //Do stuff here
    });
    

    【讨论】:

    • 这是迄今为止最简单的修复方法
    【解决方案5】:

    请记住,jQuery submit() 事件会查找: <input type="submit">, <input type="image">, or <button type="submit"> 形式为 (http://api.jquery.com/submit/)。一些框架默认 type 属性为“submit”,因此如果你试图覆盖默认值,请将 type 属性更改为其他内容,这样它就不会多次提交。

    【讨论】:

      【解决方案6】:

      发生 OpenCart 双重提交是因为 common.js 中存在提交绑定。

      通过对匹配"form-"的表单使用id模式来避免这种情况。

      示例:<form id="myform" >

      【讨论】:

        【解决方案7】:

        您可以使用此代码来解决:

        $(this).submit(function() {
        .
        .
        .
        });
        
        $(this).unbind("submit");
        

        【讨论】:

          【解决方案8】:

          我遇到了同样的问题,并使用点击修复如下。

           $('.submit_to_remote').on('click', function(){
          //Some validation or other stuff
          $(this).submit();
          });
          

          【讨论】:

            猜你喜欢
            • 1970-01-01
            • 1970-01-01
            • 2017-12-16
            • 2012-05-26
            • 2011-06-17
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 2016-07-24
            相关资源
            最近更新 更多