如何让代码等待forEach循环执行完成后再返回数据?
问题描述
以下是我的getUsers函数:
const getUsers = async (req, res) => { try { ddb.get({ TableName: "Tablename", Key: { Username: req.query.username } },(err,user) => { if(err || Object.keys(user).length === 0) { return res.status(404).json("Something went wrong") } else { const userSociety = Object.keys(user.Item.Societies)[0] ddb.get({ TableName: "Tablename", Key: { SocietyCode: userSociety } },(err, society) => { if(err || Object.keys(society).length === 0) { return res.status(400).json({ message: "Could not fetch society members" }) } else { const users = Object.keys(society.Item.SocietyMembers) const usersData = [] users.forEach(async u => { ddb.get({ TableName: "TestMyMohallaUsers", Key: { Username: u } },async (err,user) => { if(err || Object.keys(user).length === 0) { } else usersData.push({ Username: user.Item.Username, Firstname: user.Item.Name }) }) }) return res.status(200).json({ message: "Data detched successfully", Users: usersData }) } }) } }) } catch (error) { return res.status(500).json({ error: "Internal Server Error" }) } }
我希望等待forEach循环执行完成后,再通过return语句返回数据,但目前return语句返回的usersData是空数组。显然我的代码没有等待forEach执行完毕就返回了,请问该如何解决?(补充:ddb是DynamoDB的实例)
解决方法
核心问题
forEach不支持异步等待:你在forEach里用了async回调,但forEach不会等待异步操作完成,会直接执行后续代码,导致返回时usersData还没被填充。- 回调嵌套+异步混用:当前用的是DynamoDB的回调式API,嵌套层级深,还混合
async/await,时序控制混乱。
具体解决方案
步骤1:改用DynamoDB的Promise式API
AWS SDK的DynamoDB方法可以通过.promise()转换为Promise,配合async/await处理异步,避免回调地狱,更易控制时序。
步骤2:用Promise.all替代forEach处理批量异步
对于批量异步任务,用map生成异步任务数组,再通过Promise.all等待所有任务完成,确保数据全部填充后再返回。
修改后的完整代码
const getUsers = async (req, res) => { try { // 获取当前用户信息(改用Promise+await) const userResult = await ddb.get({ TableName: "Tablename", Key: { Username: req.query.username } }).promise(); if (!userResult.Item) { return res.status(404).json("Something went wrong"); } // 获取用户所属社团信息 const userSociety = Object.keys(userResult.Item.Societies)[0]; const societyResult = await ddb.get({ TableName: "Tablename", Key: { SocietyCode: userSociety } }).promise(); if (!societyResult.Item) { return res.status(400).json({ message: "Could not fetch society members" }); } // 提取社团成员用户名列表 const memberUsernames = Object.keys(societyResult.Item.SocietyMembers); // 批量生成获取成员信息的异步任务 const memberPromises = memberUsernames.map(async username => { try { const memberResult = await ddb.get({ TableName: "TestMyMohallaUsers", Key: { Username: username } }).promise(); // 仅返回有效用户数据 if (memberResult.Item) { return { Username: memberResult.Item.Username, Firstname: memberResult.Item.Name }; } return null; } catch (err) { // 单个成员获取失败时返回null,不影响整体 return null; } }); // 等待所有异步任务完成,过滤掉无效数据 const usersData = (await Promise.all(memberPromises)).filter(item => item !== null); // 返回填充完成的结果 return res.status(200).json({ message: "Data fetched successfully", Users: usersData }); } catch (error) { return res.status(500).json({ error: "Internal Server Error" }); } }
关键改进点
- 全程用
async/await替代回调,代码层级清晰,异步时序可控。 - 用
map+Promise.all确保所有成员数据获取完成后再返回响应。 - 优化空值判断逻辑(
!userResult.Item),更符合DynamoDB返回规范。 - 单个成员获取失败时返回
null,最后过滤无效数据,避免影响整体结果。
内容的提问来源于stack exchange,提问作者user15376850
相关产品推荐
相关产品推荐

