ES6 很可能会出现简单的 promise 错误
Posted
技术标签:
【中文标题】ES6 很可能会出现简单的 promise 错误【英文标题】:Likely, easy promises error with ES6 【发布时间】:2016-04-22 18:55:45 【问题描述】:我对这段代码要发疯了。我已经尝试了所有我能想到的方法,我知道这与承诺有关……但我无法让它发挥作用!
原始代码不像我分享的那么简单,但这是问题的核心:
让我们有两个填充数组和两个空数组。 然后,“crearMazo”必须运行其中一个填充数组的循环,在我的 mongodb (mongoose) 上搜索这些字符串,并将生成的 _id 推送到其中一个空数组中。好吧,它不起作用。 最后一个 console.log 显示一个空数组,即使循环内的 console.log 确实打印了数组。
我知道...我做错了承诺(显然)...但我找不到 :(
var cartas = ['Lorem', 'Lorem2', 'Lorem3', 'Lorem4', 'Lorem5', 'Lorem6', 'Lorem7', 'Lorem8'];
var cartas2 = ['Lorem', '2Lorem', '3Lorem', '4Lorem', '5Lorem', '6Lorem', '7Lorem', '8Lorem'];
var newMazo = [];
var newMazo2 = [];
let crearMazo = function (c,m)
return new Promise((resolve, reject) =>
setTimeout(() =>
for(var i in c)
Card.findOne('nombre': c[i], '_id').then( carta =>
m.push(carta._id);
);
resolve(m);
, 0);
);
;
crearMazo(cartas,newMazo)
.then(crearMazo(cartas2,newMazo2))
.then(() =>
console.log('mazo: '+ newMazo);
console.log('mazo: '+ newMazo2);
);
【问题讨论】:
我猜第二个console.log()
应该打印newMazo2
而不是newMazo
,对吧?
【参考方案1】:
您必须将回调作为参数传递给then
,而不是承诺。你可以使用
crearMazo(cartas,newMazo)
.then(() => crearMazo(cartas2,newMazo2))
.then(() =>
console.log('mazo: '+ newMazo);
console.log('mazo: '+ newMazo);
);
但正确的解决方案是并行运行它们,并使用它们各自的结果:
Promise.all([
crearMazo(cartas, []),
crearMazo(cartas2, [])
]).then(([newMazo, newMazo2]) =>
console.log('mazo1: '+ newMazo);
console.log('mazo2: '+ newMazo2);
);
您还在这里循环启动异步操作,并为它们创建多个承诺 - 无需等待其中任何一个。你会想要
function crearMazo(c, m)
return new Promise((resolve) => setTimeout(resolve, 0)) // is that actually needed?
.then(() =>
var promises = c.map(n =>
Card.findOne('nombre': n, '_id').then(carta => carta._id);
);
return Promise.all(promises);
// ^^^^^^^^^^^
).then(res =>
m.concat(res)
);
【讨论】:
感谢您的快速回答,@bergi :) 在应用正确的解决方案后我仍然遇到同样的问题 :( 我认为问题在于 mongoose 查询没有“发回”数组(我什至不知道如何“说”它,抱歉)。如果我在“m.push(carta._id); 之后添加一个“console.log('mazo query: '+ m);" ",我在循环结束时在 console.log 上得到了正确的数组。但是 mazo1 和 mazo2 仍然是空的。 哦,等等,我完全忽略了你在那里的循环中使用了 Promise。您必须在其中创建的所有 Promise 上使用Promise.all
才能等待它们。
嘿!我们到了某个地方 :) : 现在我得到了最终的数组 "mazo1: ,,,,,,,"。
这可能意味着您正在接收的对象的_id
s 是null
、undefined
或空字符串。
事实上,在 carta._id 在 console.log 打印正确的 id 之前,它不是 :( "console.log(carta._id);"。但它仍然在 mazo1 和 mazo2 之后打印它们,顺便说一句。以上是关于ES6 很可能会出现简单的 promise 错误的主要内容,如果未能解决你的问题,请参考以下文章