为何异步map内数组有值,外部却为空?MongoDB Node.js问题
问题原因与解决方案
问题根源
你遇到的核心问题是异步代码的执行顺序:
Array.map()中使用了async回调函数,每个回调都会返回一个Promise,但map本身不会等待这些异步操作完成,而是直接返回一个包含所有 Promise 的数组,主线程会继续执行后续代码。- 外部的
console.log('Out', hubs)和return res.send(hubs)是在所有异步查询完成之前执行的,此时hubs数组还未被推入任何数据,所以是空数组。而内部的console.log(hubs)是在单个异步查询完成后触发,此时已经把结果推入数组,因此能看到内容。
解决方案
方案一:用 Promise.all() 并行处理(推荐,效率更高)
利用 map 生成包含异步查询的 Promise 数组,再通过 Promise.all() 等待所有异步操作完成,直接获取完整结果数组,无需手动 push:
const data = await userSchema.findOne({_id: objectId, active: true}); const hubIdArray = data.hubs; // 并行执行所有查询,等待全部完成后拿到结果数组 const hubs = await Promise.all( hubIdArray.map(async (hubId) => { return hub_schema.findOne({id: hubId}); }) ); console.log('Out', hubs); return res.send(hubs);
方案二:用 for...of 顺序处理
如果需要按顺序执行查询(比如存在依赖关系),可以使用 for...of 配合 await:
const data = await userSchema.findOne({_id: objectId, active: true}); const hubIdArray = data.hubs; const hubs = []; // 按顺序逐个执行异步查询 for (const hubId of hubIdArray) { const hub = await hub_schema.findOne({id: hubId}); hubs.push(hub); } console.log('Out', hubs); return res.send(hubs);
内容的提问来源于stack exchange,提问作者Digvijay Singh Thakur
相关产品推荐
相关产品推荐

