简体   繁体   中英

Unit test issue with Mocha and Sinon using javascript

I am trying to use mocha and sinon to test a piece of code that is using an AWS service. Below the code:

exports.init = ({ athenaClient }) => {
  const command = {};
  command.execute = sqlCommand => {
    const params = {
      QueryString: sqlCommand,
      QueryExecutionContext: {
        Database: process.env.ATHENA_DB || "default"
      }
    };
    return athenaClient.startQueryExecution(params).promise();
  };

  return command;
};

In my test, I am mocking the athena client and injecting it into the function, and I want to test that the method startQueryExecution is called with the sqlCommand that is sent as an input. So i've been trying to create an stub on it.

This is my test:

const AWS = require("aws-sdk");
const AWS_MOCK = require("aws-sdk-mock");
const sinon = require("sinon");
const expect = require("chai").expect;

describe("Executes a sql command in Athena", async done => {
  process.env.ATHENA_DB = "default";

  it("the sqlCommand is sent to startQueryExecution", async () => {
    const SQL_COMMAND = "DROP TABLE IF EXISTS dataset_test PURGE;";

    const athenaClient = {
      startQueryExecution: params => ({})
    };

    const executeAthenaQueryCommand = require("../commands/executeAthenaQueryCommand").init(
      {
        athenaClient
      }
    );

    sinon.stub(athenaClient, "startQueryExecution");
    sinon.stub(executeAthenaQueryCommand, "execute");

    const result = await executeAthenaQueryCommand.execute(SQL_COMMAND);

    sinon.assert.calledWith(executeAthenaQueryCommand.execute, SQL_COMMAND);

    const expectedResult = {
      QueryString: SQL_COMMAND,
      QueryExecutionContext: {
        Database: "default"
      }
    };

    sinon.assert.calledWith(athenaClient.startQueryExecution, expectedResult);
  });

  after(() => {});
});

However I am getting the error:

   AssertError: expected startQueryExecution to be called with arguments 
    at Object.fail (node_modules/sinon/lib/sinon/assert.js:104:21)
    at failAssertion (node_modules/sinon/lib/sinon/assert.js:61:16)
    at Object.assert.(anonymous function) [as calledWith] (node_modules/sinon/lib/sinon/assert.js:86:13)
    at Context.it (test/executeAthenaQueryCommand.spec.js:37:22)
    at <anonymous>

Any help please?

You almost made it correct. Some notes to rectify the test is

Add return in startQueryExecution stub

This is a must so execute function is executed correctly to return promise.

sinon.stub(athenaClient, "startQueryExecution").returns({ promise: () => Promise.resolve() });

Remove stub for execute method

This is real method that we want to test and we call it in the subsequent line so we mustn't stub it.

sinon.stub(executeAthenaQueryCommand, "execute"); // remove this
sinon.assert.calledWith(executeAthenaQueryCommand.execute, SQL_COMMAND); // remove this

So the final test file will be

describe("Executes a sql command in Athena", async done => {
  ...

  it("the sqlCommand is sent to startQueryExecution", async () => {
    ...

    sinon.stub(athenaClient, "startQueryExecution").returns({ promise: () => Promise.resolve() }); // add returns

    const result = await executeAthenaQueryCommand.execute(SQL_COMMAND);

    const expectedResult = {
      QueryString: SQL_COMMAND,
      QueryExecutionContext: {
        Database: "default"
      }
    };

    sinon.assert.calledWith(athenaClient.startQueryExecution, expectedResult);
  });

  after(() => {});
});

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM