NodeJS - Unit Test DynamoDB

Introduction

This page explains how to mock dynamodb client using Sinon and Proxyqurie

Required dependencies

Install the following dependencies

npm install --save-dev sinon
npm install --save-dev proxyquire

Sample Project

Setup a sample project

# Create a sample project directory
mkdir myproject
cd myproject

# Initalize npm
npm init -y

# Install project dependencies
npm install aws-sdk

# Install Unit test framework globally (if you have not already installed)
npm install -g mocha

# Install Test dependencies
npm install --save-dev sinon
npm install --save-dev proxyquire

create a index.js file here with the following content. This script simply calls the query function of DynamoDB on a table. Change mytable, mykey, myvalue with your table name, column name, value.

'use strict';

const AWS = require('aws-sdk');
const dynamoDbClient = new AWS.DynamoDB.DocumentClient();

async function scanUsingPromise() {
    var params = {
        TableName: 'mytable',
    };

    return await dynamoDbClient.scan(params).promise();
}

function scanUsingCallback(callback) {
    var params = {
        TableName: 'mytable',
    };

    dynamoDbClient.scan(params, (err, data) => {
        callback(err, data);
    });
}

module.exports = {
    scanUsingPromise,
    scanUsingCallback
};

Sample Test Script

It is time to write a Unit test code for the above script. Create a file test/index.test.js with the following content

'use strict';

const sinon = require('sinon');
const proxyquire = require('proxyquire').noCallThru();
var assert = require('assert');

describe('DynamoDB Mock Test', function () {
    var AWS;
    var scanFunc;
    var queryFunc;
    var scriptToTest;

    before(function () {
        queryFunc = sinon.stub();
        scanFunc = sinon.stub();

        AWS = {
            DynamoDB: {
                DocumentClient: sinon.stub().returns({
                    query: queryFunc,
                    scan: scanFunc
                })
            }
        };

        scriptToTest = proxyquire('../index', {
            'aws-sdk': AWS
        });
    });

    it('Should scan using async/await and promise', async function () {
        let result = {
            id: '123'
        };
        scanFunc.withArgs(sinon.match.any).returns({
            promise: () => result
        });

        const data = await scriptToTest.scanUsingPromise();
        assert.equal(data.id, 123);
    });

    it('Should scan using callback', function (done) {
        let result = {
            id: '987'
        };
        scanFunc.withArgs(sinon.match.any).yields(null, result);

        scriptToTest.scanUsingCallback((err, data) => {
            assert.equal(data.id, 987);
            done();
        });
    });
});

Run this test using the following command

mocha