【问题标题】:dynamoDB DocumentClient not waiting inside for loop - node js 8.10dynamoDB DocumentClient 不在循环内部等待 - 节点 js 8.10
【发布时间】:2019-03-06 06:39:46
【问题描述】:

我在使用 dynamoDB 时遇到问题,它没有在 for 循环中给我查询结果。查询确实执行了,但它只在循环完成后执行:

readMatchData(JSON) {
return new Promise((resolve, reject) => {



    for (var jsonInfo of JSON.Feed.MatchData) {


        var matchID = jsonInfo['@attributes'].matchID;

        console.log("matchID: " + matchID);

        var homeTeamID = team['@attributes'].homeTeamID;


        var params = {
            TableName: "Teams",
            KeyConditionExpression: "#teamID = :teamID",
            ExpressionAttributeNames: {
                "#teamID": "teamID"
            },
            ExpressionAttributeValues: {
                ":teamID": homeTeamID
            },
            ReturnConsumedCapacity: "TOTAL"
        }

        docClient.query(params, function(err, data) {

            if (err) {
                //console.log("We have an error when looking for the team in the Teams table");
                console.log(err);

            } else {

                if (data.Count === 0) {

                    //We did not find this ID in the db so we can add it.

                    console.log("The team doesn't exist");

                } else {

                    data.Items.forEach(function(item) {

                        console.log("Team " + item.teamID + " " + item.teamName + " found in the database");

                    })

                }

            }

        });


    }




    resolve("done");

});
}

在控制台中返回我:

匹配ID:3434

匹配 ID:3543

在数据库中找到3388 Hill U23 Team

在数据库中找到 Team 44108 Bridge U23

而不是:

匹配ID:3434

在数据库中找到3388 Hill U23 Team

匹配 ID:3543

在数据库中找到 Team 44108 Bridge U23

【问题讨论】:

    标签: node.js amazon-web-services aws-lambda amazon-dynamodb


    【解决方案1】:

    问题在于docClient 调用使用了回调,如下行所示:

    docClient.query(params, function(err, data) { ... })
    

    这意味着您传递的函数在操作完成之前不会被调用,这可能需要一段时间。

    您可以告诉库将其包装在一个 Promise 中,然后等待它:

    const data = await docClient.query(params).promise()
    
    if (data.Count === 0) {
      //We did not find this ID in the db so we can add it.
      console.log('The team doesn\'t exist')
    } else {
      data.Items.forEach(function (item) {
        console.log('Team ' + item.teamID + ' ' + item.teamName + ' found in the database')
      })
    }
    

    编辑:目前您将整个函数包装在一个 Promise 中,但由于我们将其隔离为仅回调,您可能希望将其替换为看起来更像:

    async function readMatchData () {
      for (var jsonInfo of JSON.Feed.MatchData) {
    
        var matchID = jsonInfo['@attributes'].matchID
    
        console.log('matchID: ' + matchID)
    
        var homeTeamID = team['@attributes'].homeTeamID
    
        var params = {
          TableName: 'Teams',
          KeyConditionExpression: '#teamID = :teamID',
          ExpressionAttributeNames: {
            '#teamID': 'teamID'
          },
          ExpressionAttributeValues: {
            ':teamID': homeTeamID
          },
          ReturnConsumedCapacity: 'TOTAL'
        }
    
        const data = await docClient.query(params).promise()
    
        if (data.Count === 0) {
          //We did not find this ID in the db so we can add it.
          console.log('The team doesn\'t exist')
        } else {
          data.Items.forEach(function (item) {
            console.log('Team ' + item.teamID + ' ' + item.teamName + ' found in the database')
          })
        }
      }
      return 'done'
    }
    

    编辑:感谢 HMilbradt 指出该库具有内置的 promisify 函数

    【讨论】:

    • 我想指出query()的返回类型,它是一个带有promise()方法的Request对象。示例:const data = await docClient.query(params).promise()。更简单
    • @HMilbradt 好点,在我快速浏览互联网时没有注意到,相应地更新了我的答案!谢谢
    • @OllysCoding,效果很好!非常感谢,谢谢。
    猜你喜欢
    • 2020-04-01
    • 2021-08-15
    • 2021-07-14
    • 2021-09-17
    • 1970-01-01
    • 2017-05-03
    • 2017-11-01
    • 1970-01-01
    • 2019-05-22
    相关资源
    最近更新 更多