【问题标题】:Wait until AJAX is done before proceeding等到 AJAX 完成后再继续
【发布时间】:2014-09-03 02:29:37
【问题描述】:

我查看了一些 AJAX 线程来寻找我的问题,但我没有找到适合我的情况的解决方案。事情是这样的:

我有一个包含用户 cmets 的页面。这些 cmets 保存在数据库中,每次用户按下“刷新”按钮时,都会连接到数据库,并得到 cmets 的响应。如果有任何新消息,则有一个 div “有 _ 新消息”。但是,最后一条消息永远不会正确显示,因为它出现在消息加载之前。

代码如下:

AJAX 函数

function GetComments()
{
    $("#cont-comment").empty(); //div that contains the messages
    $.ajax(
    {
        url: "get.php",
        dataType: "json",
        success: function(data)
        {
            n_msg=data.length;
            for (i=0; i<n_msg; i++)
            {
                nick=data[i].nick;
                msg=data[i].msg;
                WriteNewComment(nick,msg);
                num_comments=document.getElementsByClassName("comment-msg").length;
            }
        } 
    });
}

这就是问题所在。

$("#refresh").click(function()
{
    num_comments_before=num_comments;
    GetComments();
    alert("done");
});

“完成”消息出现在新 cmets 之前。我希望消息“完成”只会在新 cmets 出现时出现 - 当 AJAX 完成时。

【问题讨论】:

    标签: jquery ajax loaded


    【解决方案1】:

    由于 ajax 是一个异步调用,浏览器会在您进行 ajax 调用后立即生成一个线程并继续其流程,这就是您的“完成”消息出现在新 cmets 之前的原因。理想情况下,除非非常需要,否则不应阻止您的代码。

    你可以在回调中调用alert('done')函数如下图...

     function GetComments(alertFunction)
    {
        $("#cont-comment").empty(); //div that contains the messages
        $.ajax(
        {
            url: "get.php",
            dataType: "json",
            success: function(data)
            {
                n_msg=data.length;
                for (i=0; i<n_msg; i++)
                {
                    nick=data[i].nick;
                    msg=data[i].msg;
                    WriteNewComment(nick,msg);
                    num_comments=document.getElementsByClassName("comment-msg").length;
                }
    
              **alertFunction();**
            } 
        });
    }
    
    
    
    $("#refresh").click(function()
    {
        num_comments_before=num_comments;
        GetComments(alertFunction);
    
    });
    
    function alertFunction(){
      alert("done");
    }
    

    【讨论】:

      【解决方案2】:

      虽然 jQuery 没有正确遵守 Promises/A spec,但 $.ajax() 方法会返回一个 deferred object,您可以使用它来处理您的响应逻辑。这是它可以工作的一种方式:

      $.when(getComments).then(processComments);
      
      function getComments() {
          $("#cont-comment").empty();
          return $.ajax({
              url: "get.php",
              dataType: "json",
      
          });
      }
      
      function processComments(data) {
          n_msg=data.length;
          for (i=0; i<n_msg; i++) {
              nick=data[i].nick;
              msg=data[i].msg;
              WriteNewComment(nick,msg);
              num_comments=document.getElementsByClassName("comment-msg").length;
          }
          alert("done");
      }
      

      在 JavaScript 中,同步做事通常不被认为是最佳实践,回调方法是可以的,但它存在多嵌套的疯狂和麻烦的错误处理。

      【讨论】:

        【解决方案3】:

        上面的cmets是正确的。您需要在回调中进行更新。关于您的代码的几个调用。你应该总是var你的变量。不这样做,在 javascript 中,将变量添加到全局范围(这很糟糕!)。此外,最好使用 K&R 样式的大括号(在同一行而不是在新行上打开),因为使用 Allman 样式有时会导致问题。 link to article

        如果您想使用更现代的方法,那么我建议您使用 jquery $.when.done() 进行 ajax 调用。

        $.when(GetComments()).done(function(data){
          var n_msg = data.length, i=0, nick, msg, num_comments=0;
          n_msg = data.length;
          for (; i<n_msg; i++) {
            nick = data[i].nick;
            msg = data[i].msg;
            WriteNewComment(nick,msg);
            num_comments=document.getElementsByClassName("comment-msg").length;
          }
          alert('done');
        });
        

        【讨论】:

        • 这里是 $.when 上 jquery api 文档的链接:api.jquery.com/jQuery.when
        • 谢谢!我对 $.when 一无所知。看起来是个不错的选择。我也很欣赏你关于变量(我知道,我的错)和样式大括号的提示。
        【解决方案4】:

        如果添加:

        异步:假

        对于您的 ajax 调用,您的 javascript 将等待 ajax 函数返回(成功或错误),然后再继续。

        http://api.jquery.com/jquery.ajax/

        【讨论】:

        • 已弃用和不鼓励使用异步,而应使用回调。
        • 成功了,谢谢!巴拉,我也很感谢你的回应。当我让它全部运行时,我会使用你的选项。非常感谢。
        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2011-07-21
        • 2013-04-25
        • 2019-11-01
        • 2021-05-06
        • 2021-05-21
        相关资源
        最近更新 更多