jQuery $ .when不等待延期链完成ajax调用(jQuery $.when does not wait for deferred chain to complete ajax calls)

编程入门 行业动态 更新时间:2024-10-22 19:48:28
jQuery $ .when不等待延期链完成ajax调用(jQuery $.when does not wait for deferred chain to complete ajax calls)

在这里,我尝试按顺序加载几个JS文件。 问题是$.when不等待链条完成时。 但最后的$.Deferred.then按预期工作。 工作时我应该做些什么来赚取$.when ?

var urls = [
    "https://cdnjs.cloudflare.com/ajax/libs/jqueryui/1.12.1/jquery-ui.js",
    "https://cdnjs.cloudflare.com/ajax/libs/photoswipe/4.1.2/photoswipe.js",
    "https://cdnjs.cloudflare.com/ajax/libs/photoswipe/4.1.2/photoswipe-ui-default.js"
];
var xxx = $.Deferred();
xxx.then(function() {
        options = {
            dataType: "script",
            url: urls[0],
            cache: false
        };
        return $.ajax(options).promise();
    })
    .then(function() {
        options = {
            dataType: "script",
            url: urls[1],
            cache: false
        };
        return $.ajax(options).promise();
    })
    .then(function() {
        options = {
            dataType: "script",
            url: urls[2],
            cache: false
        };
        return $.ajax(options).promise();
    }).then(function() {
        $("body").append("This is correct. All files are loaded.<br>");
    });

$.when(xxx).done(function() {
    $("body").append("This is wrong. JS files are not loaded yet.<br>");
});
xxx.resolve(); 
  
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script> 
  
 

小提琴 https://jsfiddle.net/ergec/fmrj6qgp/

Here i try to load several JS files sequentially. Problem is $.when does not wait for the chain to complete. But the last $.Deferred.then works as expected. What should i do to make $.when work?

var urls = [
    "https://cdnjs.cloudflare.com/ajax/libs/jqueryui/1.12.1/jquery-ui.js",
    "https://cdnjs.cloudflare.com/ajax/libs/photoswipe/4.1.2/photoswipe.js",
    "https://cdnjs.cloudflare.com/ajax/libs/photoswipe/4.1.2/photoswipe-ui-default.js"
];
var xxx = $.Deferred();
xxx.then(function() {
        options = {
            dataType: "script",
            url: urls[0],
            cache: false
        };
        return $.ajax(options).promise();
    })
    .then(function() {
        options = {
            dataType: "script",
            url: urls[1],
            cache: false
        };
        return $.ajax(options).promise();
    })
    .then(function() {
        options = {
            dataType: "script",
            url: urls[2],
            cache: false
        };
        return $.ajax(options).promise();
    }).then(function() {
        $("body").append("This is correct. All files are loaded.<br>");
    });

$.when(xxx).done(function() {
    $("body").append("This is wrong. JS files are not loaded yet.<br>");
});
xxx.resolve(); 
  
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script> 
  
 

Fiddle https://jsfiddle.net/ergec/fmrj6qgp/

最满意答案

你的方法不起作用,因为你从同一个承诺中创建了两个分支。 你有相当于:

var xxx = $.Deferred(); xxx.then(...).then(...); // promise chain 1 xxx.then(...) // promise chain 2 xxx.resolve(); // start the race between the two promise chains

这只是两个单独的承诺链之间的竞争,这些承诺链没有排序或协调。 无论哪个花费较少的时间执行都将首先达到目的。 它们之间没有协调。

参见Chaining与Branching和p.then()。then()与p.then(); p.then()作进一步解释。

而且,你使用$.when(xxx).done()是不必要的,根本不是问题的一部分。 你会得到与xxx.done()相同的结果。


您只能使用一个承诺链来修复它:

p.then(...).then(...).then(...)

然后,一切都按顺序排列和协调。

var urls = [ "https://cdnjs.cloudflare.com/ajax/libs/jqueryui/1.12.1/jquery-ui.js", "https://cdnjs.cloudflare.com/ajax/libs/photoswipe/4.1.2/photoswipe.js", "https://cdnjs.cloudflare.com/ajax/libs/photoswipe/4.1.2/photoswipe-ui-default.js" ]; let options = { dataType: "script", url: urls[0], cache: false }; $.ajax(options).then(function() { let options = { dataType: "script", url: urls[1], cache: false }; return $.ajax(options); }).then(function() { let options = { dataType: "script", url: urls[2], cache: false }; return $.ajax(options).then(function() { $("body").append("Last script loaded<br>"); }); }).then(function() { $("body").append("This is correct. All files are loaded.<br>"); });

工作示例: https : //jsfiddle.net/jfriend00/tLp68a3q/


或者,如果你仍然想用var xxx = $.Deferred()初始化你的链,那么你可以稍后用xxx.resolve()启动它,那么你也可以这样做,但你不能使用xxx.then()或$.when(xxx)因为这是一个完全独立的分支,根本没有链接到另一个承诺链。

以$.Deferred()开头的工作示例: https : $.Deferred()

Your method does not work because you create two branches off the same promise. You have the equivalent of:

var xxx = $.Deferred(); xxx.then(...).then(...); // promise chain 1 xxx.then(...) // promise chain 2 xxx.resolve(); // start the race between the two promise chains

That is simply a race between two separate promise chains that are not sequenced or coordinated. Whichever one takes less time to execute will get to its end first. There is zero coordination between them.

See Chaining vs. Branching and p.then().then() vs. p.then(); p.then() for further explanation.

And, your use of $.when(xxx).done() is unnecessary and not really part of the issue at all. You would get the same result with xxx.done().


You can fix it by only using one promise chain:

p.then(...).then(...).then(...)

Then, everything is properly sequenced and coordinated.

var urls = [ "https://cdnjs.cloudflare.com/ajax/libs/jqueryui/1.12.1/jquery-ui.js", "https://cdnjs.cloudflare.com/ajax/libs/photoswipe/4.1.2/photoswipe.js", "https://cdnjs.cloudflare.com/ajax/libs/photoswipe/4.1.2/photoswipe-ui-default.js" ]; let options = { dataType: "script", url: urls[0], cache: false }; $.ajax(options).then(function() { let options = { dataType: "script", url: urls[1], cache: false }; return $.ajax(options); }).then(function() { let options = { dataType: "script", url: urls[2], cache: false }; return $.ajax(options).then(function() { $("body").append("Last script loaded<br>"); }); }).then(function() { $("body").append("This is correct. All files are loaded.<br>"); });

Working example: https://jsfiddle.net/jfriend00/tLp68a3q/


Or, if you still wanted to initialize your chain with var xxx = $.Deferred() so you could start it later with xxx.resolve(), then you can do that too, but you can't use xxx.then() or $.when(xxx) because that is a completely separate branch that is not linked to the other promise chain at all.

Working example starting with $.Deferred(): https://jsfiddle.net/jfriend00/y5n3hb99/

更多推荐

本文发布于:2023-04-28 04:11:00,感谢您对本站的认可!
本文链接:https://www.elefans.com/category/jswz/34/1329793.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
本文标签:wait   ajax   jQuery   deferred   calls

发布评论

评论列表 (有 0 条评论)
草根站长

>www.elefans.com

编程频道|电子爱好者 - 技术资讯及电子产品介绍!