我有一个表名数组,所以我需要获取三个表的响应。请参阅以下代码。一旦数据附加到dom我需要调用successMessage方法,现在我使用setTimeout如何在这种情况下使用promise
let lists = ['table1', 'table2', 'table3']
lists.map(list => {
$.ajax({
url:`${rootUrl}/api/('${list}')`,
type: 'GET',
headers: {
accept: 'application/json'
},
success: res => dataDisplay(res),
error: err => console.log(JSON.stringify(err))
})
})
// displaying data
const dataDisplay = (res) => {
switch(res.TableName){
case 'Table1':
$("#tbl1 p").text(res.TableOriginalName)
$("#tbl1 .content p").text(res.TableDescription)
break;
case 'Table2':
$("#tbl2 p").text(res.TableOriginalName)
$("#tbl2 .content p").text(res.TableDescription)
break;
case 'Table3':
$("#tbl3 p").text(res.TableOriginalName)
$("#tbl3 .content p").text(res.TableDescription)
break;
default:
return
}
}
// successfully data appended
const successMessage = () => alert("data appended successfully")
// calling the success method once data is appended
setTimeout(successMessage, 3000)
在显示消息之前,您将使用Promise.all
等待所有这些请求完成。首先,建立一个承诺数组:
var promises = lists.map(list => $.ajax({
url:`${rootUrl}/api/('${list}')`,
type: 'GET',
headers: {
accept: 'application/json'
},
success: res => dataDisplay(res),
error: err => console.log(JSON.stringify(err))
}));
然后等待他们完成
Promise.all(promises).then(() => alert("data appended successfully"));
您也可以将$.when
用于相同的目的,但调用它很尴尬:
$.when.apply($, promises).done(() => ...);
在评论中你已经说过dataDisplay
加载了一堆图像,你需要延迟调用successMessage
,直到这些图像加载完毕。要做到这一点,你需要在图像上观察load
事件。这可能有点松鼠,因为图像可以在你挂钩事件之前加载,所以我们也想要使用图像的complete
标志。这些方面的东西:
Promises.all(/*...*/).then(() => {
// Get all images in the tables we added to
let imgs = $("#tbl1 img, #tbl2 img, #tbl3 img");
// Hook up a function to check for completed images when we
// see a `load` event on any of them, and fire that proactively
imgs.on("load", checkComplete);
checkComplete();
function checkComplete() {
// Count any incomplete images; remove the handler from any
// complete image and remove it from our `imgs` set
let incomplete = 0;
imgs.get().forEach(img => {
if (img.complete || img.error) {
$(img).off("load", checkComplete);
imgs = imgs.not(img);
} else {
++incomplete;
}
});
if (incomplete == 0) {
// They're all done!
successMessage();
}
}
});
这不是我的头脑,可能需要一些调整,但它应该让你以正确的方式前进。
您可以尝试以下代码:
let tableNames = ['table1', 'table2', 'table3']
let promiseArr = tableNames.map((table) => {
return new Promise((resolve, reject) => {
$.ajax({
url:`${rootUrl}/api/('${list}')`,
type: 'GET',
headers: {
accept: 'application/json'
},
success: (res) => {
dataDisplay(res);
resolve(table);
},
error: (err) => {
console.log(JSON.stringify(err));
reject(table);
}
});
}).catch((e) => {
// if call to any of the table's url fails
// it will come here, var 'e' contains
// that table name, handle here
console.log(e + " has fails"); return e;
});
});
Promise.all(promiseArr).
then((result) => {
// this will run regardless of, if call to any table fails
console.log("success")
})
.catch((result) => {
console.log(result + " fails");
});
这将异步调用表,最后到Promise.all()的then(),即使调用某些表失败