jquery ajax beforesend

use*_*179 27 javascript jquery jquery-blockui

我有一个简单的ajax调用,它在beforeSend和on complete上执行一个函数.它们执行得很好但是beforeSend"看似"在成功之后才会被执行.在发送之前有一个"请稍候"通知.如果我在beforeSend中的函数之后放了一个休息,那么它将显示该通知然后点击成功.没有断点,那么它将坐在那里等待响应时思考,然后我的请等待通知将在成功命中后出现几分之一秒.所需的功能是在请求发送后立即显示通知,以便在等待响应时显示.

        $.ajax({
            type : 'POST',
            url : url,
            async : false,
            data : postData,
            beforeSend : function (){
                $.blockUI({
                    fadeIn : 0,
                    fadeOut : 0,
                    showOverlay : false
                });
            },
            success : function (returnData) {
                //stuff
            },
            error : function (xhr, textStatus, errorThrown) {
                //other stuff
            },
            complete : function (){
                $.unblockUI();
            }
        });
Run Code Online (Sandbox Code Playgroud)

Ste*_*eve 26

你的问题是async:false旗帜.除了它是不好的做法(实际上只在非常有限的情况下才有意义),它实际上与其余代码的执行顺序混淆.原因如下:

它似乎在blockUI代码中的某个地方设置了一个setTimeout.结果,blockUI代码等待的时间非常短.由于队列中的下一条指令是ajax()调用,因此blockUI执行位于其后面.而且由于您正在使用async:false,它必须等到完成ajax调用完成才能运行.

详细而言,这是发生的事情:

  • 你打电话 blockUI
  • blockUI有一个setTimeout并在超时完成后执行(即使超时长度为0,下一行将ajax()首先运行)
  • ajax()调用with async:false,这意味着JS会停止所有内容,直到请求返回
  • ajax() 成功返回,JS执行可以继续
  • 内部blockUI代码中的setTimeout 可能已经结束,因此将在下一步执行
  • 它看起来像是blockUI一部分运行success,但实际上,由于超时,它刚刚排队

如果你不使用async:false,执行将如下:

  • 你打电话 blockUI
  • blockUI有一个setTimeout并在超时完成后执行(即使超时长度为0,下一行将ajax()首先运行)
  • ajax() 被调用并向服务器发送请求.
  • 当它连接到服务器时,正常的JS执行继续
  • 内部blockUI代码中的setTimeout 可能已经结束,因此将在下一步执行
  • blockUI文本显示出来
  • 除非在某处有更多JS代码,否则JS执行完成直到执行AJAX successcomplete回调

以下是一些用于演示此问题的jsFiddle示例:

示例1:这是您遇到的情况.该blockUI文本不显示,直到后ajax调用执行.

示例2:这与您的情况完全相同,但alertajax通话之前.因为有一个alert,内部超时blockUIblockUI文本的外观放在后面alert而不是之后ajax.

示例3:这就是它应该如何工作async:false


Moh*_*dil 6

这很可能是因为async : false.由于你的调用是同步的,在你调用$.ajax()函数开始之后,没有任何事情发生,直到收到响应,然后你的代码下一件事就是success处理程序

为了使它工作,你可以做这样的事情

$.blockUI({
        fadeIn : 0,
        fadeOut : 0,
        showOverlay : false
});
// and here goes your synchronous ajax call
$.ajax({
            type : 'POST',
            url : url,
            async : false,
            data : postData,
            success : function (returnData) {
                //stuff
            },
            error : function (xhr, textStatus, errorThrown) {
                //other stuff
            },
            complete : function (){
                $.unblockUI();
            }
     });
Run Code Online (Sandbox Code Playgroud)

  • 我删除了beforeSend并完成并在.ajax请求之前和之后放置逻辑但是功能没有改变 (2认同)