在$ .ajax里面嵌套$ .ajax - 非常奇怪的问题

时间:2013-12-03 11:53:21

标签: javascript jquery

让我们从这里开始 - 我已经为所有未来的AJAX请求定义了基本设置,比如这个

$.ajaxSetup({
  beforeSend : function(){
      $("#ajax-loader").dialog({
         modal : true 
      });
  },

  complete : function(){
     $("#ajax-loader").dialog("hide");
  }
});

现在,我有一个表单,我的用户可以上传他们的简历和图片。当表单有效时,我允许上传他们的图片。它的工作原理如下:

$("#send").click(function(e){
   e.preventDefault();

   $.ajax({
      data : $("#bio-form").serialize(),
      url : "/validate.ajax",
      success : function(response) {
        // If AJAX-validator returns "1" then a form is valid  
        if (response == "1"){

            // Now I start to upload photos, like
            // this

            var formData = new FormData(document.getElementById('upload-form'));

            $.ajax({
               processData  : false,
               contentType  : false,
               cache    : false,
               data         : formData,
               success : function(response) {
                  alert(response);
               }
            });
        }
      }
   });

});

问题

ajax-upload开始后,我希望显示$("#ajax-loader")。完成后,应根据我在$.ajaxSetup中定义的设置自动关闭。

BUT ... 它在文件上传1秒后立即显示和消失。我知道ajax请求没有完成,因为我在1-2分钟后获得了成功的消息(上传的照片)。

我尝试更改async: false并开始按预期工作===将文件上传到服务器时出现模式并在完成后显示消息:

data        : formData,
async       : false,
processData : false,

问题

async : true设置为默认模式(true)时,是否可以执行相同的操作?我不希望在上传过程中冻结浏览器!

2 个答案:

答案 0 :(得分:0)

正如您所发现的,Ajax是一种异步技术 - 意味着它按照自己的计划运行

使Ajax同步导致各种问题(使用async:false实际上导致浏览器在执行请求时冻结)

我提到你可能想要解决几个问题:


为什么嵌套Ajax?

在我看来,在当前网络状态下嵌套Ajax请求是不好的做法。这通常意味着您的系统出了问题。并发请求很好 - 但嵌套我会像瘟疫一样避免


Ajax回调

如果您可以将Ajax请求发送到单个实体,我会考虑使用Ajax Callbacks来创建您想要的结果

Ajax回调通过使用Ajax作为函数的一部分来工作,其中成功&错误回调由父函数的几个不同部分处理。这是一个例子:

 function create_modal(o){

        fetch_modal(o.ajax, function(data){
           //do success stuff here
        }, function(data){
           //do error stuff here
        });

 }

 function fetch_modal(link, success, error) {
     $.ajax({
        url: link,
        success: function(data) { success(data); },
        error: function(data)   { error(data); }
     });
 } 

答案 1 :(得分:0)

问题是ajaxSetup。您必须在上传照片时遵循启用/禁用方法。让我澄清理解。您希望显示加载程序以使用户熟悉他/她必须等待验证过程完成。验证成功后,您将开始上传文件。在上传文件时,您希望允许用户与页面进行交互。

要实现这一目标,您必须执行以下操作,

function ajaxSetup(mode) {
    var options = {};
    if (mode === "on") {
        options = {
            beforeSend : function() {
                $("#ajax-loader").dialog({
                    modal : true
                });
            },

            complete : function() {
                $("#ajax-loader").dialog("hide");
            }
        };
    } else {
        options = {
            beforeSend : function() {
            },

            complete : function() {
            }
        };
    }
    $.ajaxSetup(options);
}

按照以下方式制作你的ajax请求,

ajaxSetup("on");
$("#send").click(function(e) {
    e.preventDefault();

    $.ajax({
        data : $("#bio-form").serialize(),
        url : "/validate.ajax",
        success : function(response) {
            // If AJAX-validator returns "1" then a form is valid
            if (response == "1") {

                // Now I start to upload photos, like
                // this

                var formData = new FormData(document.getElementById('upload-form'));
                ajaxSetup("off"); //Here second-time seem-less displaying of loader will be avoided.
                $.ajax({
                    processData : false,
                    contentType : false,
                    cache : false,
                    data : formData,
                    success : function(response) {
                        alert(response);
                    }
                });
                ajaxSetup("on");
            }
        }
    });
});

注意:我没有经过测试的代码。如果有任何语法或拼写错误,请确保。