Search code examples
node.jsamazon-s3aws-lambdaamazon-dynamodbalexa-skills-kit

AWS Lambda using s3 getObject function and putItem function to insert it into DynamoDB but nothing happens


this is the node.js code:

'use strict';

const AWS = require("aws-sdk");

AWS.config.update({
    region: 'eu-west-1'});

const docClient = new AWS.DynamoDB.DocumentClient();

const tableName = 'Fair';

const s3 = new AWS.S3();

exports.handler = async (event) => {
    var getParams = {
        Bucket: 'dataforfair', //s3 bucket name
        Key: 'fairData.json' //s3 file location
    }
    
    const data = await s3.getObject(getParams).promise()
    .then( (data) => {
        //parse JSON 
        let fairInformations = JSON.parse(data.Body.toString());

        fairInformations.forEach(function(fairInformationEntry) {
            console.log(fairInformationEntry);
            var params = {
                TableName: tableName,
                Item: {
                    "year": fairInformationEntry.year,
                    "fairName":  fairInformationEntry.fairName,
                    "info": fairInformationEntry.info
                }
            };
        
            docClient.put(params, function(err, data) {
                console.log('*****test');
            if (err) {
                console.error("Unable to add fairInformation", fairInformationEntry.fairName, ". Error JSON:", JSON.stringify(err, null, 2));
            } else {
                console.log("PutItem succeeded:", fairInformationEntry.fairName);
            }
            });
        });
       })
       .catch((err) => {
           console.log(err);
       });
      

    const response = {
        statusCode: 200,
        body: JSON.stringify(data),
    };
    return response;
};

Hello everyone,

I want to put the data into the Dynamo DB after getting the JSON file from the s3 Bucket. Getting the JSON works and the console.log(fairInformationEntry); is also still triggered, but the docClient.put() never gets called. I am getting no error, nothing. I do not know what is wrong and why it is not working. I have the right IAM role and access to everything I need.

I hope you can help me!


Solution

  • The problem is mixup of promise, callback and async/await. You are also trying to do asynchronous operation inside foreach. The code should look something like this

    "use strict";
    
    const AWS = require("aws-sdk");
    
    AWS.config.update({
      region: "eu-west-1"
    });
    
    const docClient = new AWS.DynamoDB.DocumentClient();
    
    const tableName = "Fair";
    
    const s3 = new AWS.S3();
    
    exports.handler = async event => {
      var getParams = {
        Bucket: "dataforfair", //s3 bucket name
        Key: "fairData.json" //s3 file location
      };
    
      const data = await s3.getObject(getParams).promise();
      //parse JSON
      let fairInformations = JSON.parse(data.Body.toString());
    
      await Promise.all(
        fairInformations.map(fairInformationEntry => {
          console.log(fairInformationEntry);
          var params = {
            TableName: tableName,
            Item: {
              year: fairInformationEntry.year,
              fairName: fairInformationEntry.fairName,
              info: fairInformationEntry.info
            }
          };
          return docClient.put(params).promise();
        })
      );
    
      const response = {
        statusCode: 200,
        body: JSON.stringify(data)
      };
      return response;
    };
    
    

    Hope this helps