链式jQuery.then() -每个下一个只在前一个解析完成后执行

Chained jQuery.then() - is each next one executing only after previous resolve completely

本文关键字:一个 执行 then jQuery 下一个 链式      更新时间:2023-09-26

我有这样的代码

$.when(
    // I checked the first one and assume all return promises
    datacontext.entity1.getPromise({ ...options... }),
    datacontext.entity2.getPromise({ ...options... }),
    datacontext.entity3.getPromise({ ...options... }),
    datacontext.entity4.getPromise({ ...options... }),
    datacontext.entity5.getPromise({ ...options... }),
    datacontext.entity6.getPromise({ ...options... }),
    datacontext.entity7.getPromise({ ...options... }),                    )
.then(
    // some more similar calls returning promises
    datacontext.entity8.getPromise({ ...options... }),
    datacontext.entity9.getPromise({ ...options... }),
    datacontext.entity10.getPromise({ ...options... }),
    datacontext.entity11.getPromise({ ...options... }),                    
)
.then(function() {
    // do work with the results
});

如果我理解正确的话,第一个then()的执行应该在when()中的所有延迟被解决之前才开始。对吗?我是否应该期望两个then()部分相同-即// do work with the results不应该在之前的then()的所有调用都解决之前到达?在Chrome中似乎是真的,但在FF中,我在所有延迟解决之前击中了最后一个then()

那么根据评论,这是正确的链接方式吗?

$.when(
    // I checked the first one and assume all return promises
    datacontext.entity1.getPromise({ ...options... }),
    datacontext.entity2.getPromise({ ...options... }),
    datacontext.entity3.getPromise({ ...options... }),
    datacontext.entity4.getPromise({ ...options... }),
    datacontext.entity5.getPromise({ ...options... }),
    datacontext.entity6.getPromise({ ...options... }),
    datacontext.entity7.getPromise({ ...options... })
)
.then(function() {
    $.when(
        // some more similar calls returning promises
        datacontext.entity8.getPromise({ ...options... }),
        datacontext.entity9.getPromise({ ...options... }),
        datacontext.entity10.getPromise({ ...options... }),
        datacontext.entity11.getPromise({ ...options... })
    )
    .then(function() {
        // do work with the results
    });
})

在jQuery中,$.when(和标准中的Promise.all)接受一个承诺列表,并返回一个承诺,当所有的承诺都解决时,它就会解决。

.then方法发出继续的信号,并接受一个完成和拒绝处理程序。当你从.then返回一个承诺时,只有当返回的承诺被解决时,它才会继续。当你返回一个值,它将继续"立即"。

那么,你要做的就是从第二个then处理程序返回一个$.when:

$.when(
    // I checked the first one and assume all return promises
    datacontext.entity1.getPromise({ ...options... }),
    datacontext.entity2.getPromise({ ...options... }),
    datacontext.entity3.getPromise({ ...options... }),
    datacontext.entity4.getPromise({ ...options... }),
    datacontext.entity5.getPromise({ ...options... }),
    datacontext.entity6.getPromise({ ...options... }),
    datacontext.entity7.getPromise({ ...options... }))
.then(function(){ // our handler, note that its params are the resolution values
    return $.when( // which will resolve when this composite promise will resolve
    // some more similar calls returning promises
    datacontext.entity8.getPromise({ ...options... }),
    datacontext.entity9.getPromise({ ...options... }),
    datacontext.entity10.getPromise({ ...options... }),
    datacontext.entity11.getPromise({ ...options... }),                    
    )
})
.then(function() {
    // do work with the results
});

如果我可以建议:

  1. 使用一个真正的承诺实现,jQuery延迟对象是非常有限的。
  2. 使用返回值而不是全局/闭包变量从承诺传递数据。