我有3个函数可以对后端系统进行aync调用:fnOne,fnTwo,fnThree。我知道我做的不正确,但是找不到正确的方法。
我首先尝试在每次完成后称呼他们:
但是,fnOne中已经有一个延迟的对象,解决该问题时,它正在兑现我的承诺。
$.when(oController._fnOne()).done(function(){
console.log("fn one complete");
});
功能
_fnOne: function(){
var oController = this;
//when the deferred is done in _checkInstanceStatus, it is resolving the above, rather than the pDeferred in this function resolving the above.
$.when(oController._checkInstanceStatus(oParams)).done(function(oStatusData) {
//does some stuff
return $.Deferred(function() {
var pDeferred = this;
//does a call for data and upon success i will resolve ..
pDeferred.resolve();
});
});
}
其他功能
_checkInstanceStatus: function(oParams){
return $.Deferred(function() {
var pDeffered = this;
//does a call for data and upon success i will resolve...
pDeffered.resolve(data);
});
});
},
然后计划是尝试将它们链接起来,以便它们一个接一个地运行,如下所示:
$.when(oController._fnOne())
.then(oController._fnTwo())
.then(oController._fnThree())
.done(function(){
console.log("all complete!");
});
最佳答案
有两件事:
如果要传递,则无需使用$.when
。fnOne
(可能还有其他)需要返回一个promise / Deferred,以便您知道它何时完成。由于它使用的是_checkInstanceStatus
并返回Deferred,因此可以使用then
来实现:
所以fnOne
可能看起来像这样:
fnOne: function() {
var oController = this;
return oController.__checkInstanceStatus(oParams).then(function(oStatusData) {
var pDeferred = $.Deferred();
callAmazon(function() {
if (/*successful*/) {
pDeferred.resolve();
} else {
pDeferred.reject();
}
});
return pDeferred.promise(); // Or just the Deferred if you like, but
// normally you want to share promises, not
// Deferred objects
});
}
注意,它如何返回调用
then
的结果,这是通过调用then
创建的承诺。该承诺将根据您从then
处理程序返回的承诺来解决。您将对其他功能遵循相同的模式。
要将它们一个接一个地链接,您可以这样做:
oController._fnOne()
.then(oController._fnTwo) // Notice no () on that, we're passing the
.then(oController._fnThree) // function in, not calling it. Same on this line.
.then(function() {
console.log("all complete!");
})
.catch(function(error) {
// Do something about the error
});
(我假设
_fnOne
和fnOne
是相同的函数。)我假设相对较新的jQuery在Deferreds中具有Promises支持。
旁注:我将改用本机Promises(必要时使用polyfill以支持旧的浏览器),而不是使用jQuery的
Deferred
,它具有丰富的历史,并且API变得笨拙。 :-)带有原生承诺:
fnOne: function() {
var oController = this;
return oController.__checkInstanceStatus(oParams).then(function(oStatusData) {
return new Promise(function(resolve, reject) {
callAmazon(function() {
if (/*successful*/) {
resolve();
} else {
reject();
}
});
});
});
}
用法是相同的(因为我使用了第一个示例中已添加到Deferred的Promise API)。
关于javascript - 延期 promise -每次完成后一次运行功能,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/43784439/