我有这段代码:
function ProductObj(product, i) {
var self = this;
self.photo = product.photos.medium_half;
self.title = product.name;
self.tagline = product.tagline;
self.url = product.url;
self.htmlView = "";
self.index = i;
//this async call is slow, very slow
self.updateHTML = function() {
return new Promise(resolve => {
$.get('product-template.html', function (template) {
self.htmlView = template.replace('{image}', self.photo)
.replace('{title}', self.title)
.replace('{tagline}', self.tagline)
.replace('{url}', self.url);
console.log('updateHTML ' + self.index + ' ran');
resolve();
});
});
};
}
当调用self.updateHTML时,同时调用self.updateDOM
self.updateDOM = function() {
return new Promise(resolve => {
var thisHTML = '';
for( var i = 0; i < self.products.length; i++) {
if (i % 3 === 0 ) {
thisHTML += "<div class='row'>";
console.log('START')
}
thisHTML += self.products[i].htmlView;
if ((i % 3 === 2) || i === (self.products.length - 1) ) {
thisHTML += "</div>";
console.log('finish')
}
if(i === (self.products.length -1)) {
$("#content").append(thisHTML);
}
}
resolve();
})
}
很自然地,我用promises试图解决这个问题
page.getProducts('data.json')
.then( page.updateProductHTML )
.then( page.updateDOM )
.then( someOtherFunction );
首先执行 Page.getProducts
并向page.updateProductHTML
返回一个承诺。到目前为止,page.updateProductHTML
中的承诺在self.updateHTML
完成分配并且updateDOM
被解雇之前就已解决,但在完成之前需要来自updateHTML的值
问题来自于此page.updateProductHTML
,因为它运行此代码
self.updateProductHTML = function() {
return new Promise(resolve => {
for( var i = 0; i < self.products.length; i++){
self.products[i].updateHTML();
}
resolve();
})
};
我尝试将上述代码包装在一个promise中,并在for循环之外解析,但$.get()
调用仍然有效
.then
}
如果在page.updateProductHTML
完成调用之前,如何强制page.updateProductHTML
无法解决?
小概述我想要这个订单self.updateHTML
答案 0 :(得分:4)
您应该使用Promise.all()
:
self.updateProductHTML = function() {
return Promise.all(self.products.map(product => product.updateHTML()));
};
答案 1 :(得分:1)
你可以使用promise.all,等待所有的promise都被解析,然后执行依赖于早期方法的其他方法。
我的Codepen链接
就是一个例子
self.updateProductHTML = function() {
var updateMethods = [];
for (var i = 0; i < self.products.length; i++) {
updateMethods.push(self.products[i].updateHTML());
}
return Promise.all(updateMethods);
}
self.updateDOM = function() {
for (var i = 0; i < self.products.length; i++) {
if (i % 3 === 0) {
thisHTML += "<div class='row'>";
console.log('START')
}
thisHTML += self.products[i].htmlView;
if ((i % 3 === 2) || i === (self.products.length - 1)) {
thisHTML += "</div>";
console.log('finish')
}
if (i === (self.products.length - 1)) {
$("#content").append(thisHTML);
}
}
}
updateProductHTML().then(updateDOM);
&#13;