Как смоделировать функцию в другой функции nodejs - PullRequest
0 голосов
/ 16 ноября 2018

Попытка написать юнит-тест для приведенного ниже модуля в /utility/sqsThing.js.Однако я испытываю трудности с насмешкой над методом sqs.sendMessage.Кто-нибудь знает, как я должен идти об этом.Я использую библиотеку sinon и mocha для запуска тестов.

Функция, которую я пытаюсь протестировать utility/sqsThing.js:

const AWS = require('aws-sdk');
AWS.config.update({ region: 'us-east-1' });
const sqs = new AWS.SQS({ apiVersion: '2012-11-05' });
const outputQueURL = 'https:awsUrl';

const SQSOutputSender = (results) => {
  const params = {
    MessageBody: JSON.stringify(results),
    QueueUrl: outputQueURL,
  };
  // Method that I want to mock
  sqs.sendMessage(params, function (err, data) {
    if (err) {
      console.log('Error');
    } else {
      console.log('Success', data.MessageId);
    }
  });
};

Моя попытка издеваться над sqs.Метод sendMessage в юнит-тесте sqsThingTest.js:

const sqsOutputResultSender = require('../utility/sqsThing');
const AWS = require('aws-sdk');
const sqs = new AWS.SQS({ apiVersion: '2012-11-05' });

const mochaccino = require('mochaccino');

const { expect } = mochaccino;
const sinon = require('sinon');


describe('SQS thing test', function() {
    beforeEach(function () {
        sinon.stub(sqs, 'sendMessage').callsFake( function() { return 'test' });
    });

    afterEach(function () {
        sqs.sendMessage.restore();
    });

  it('sqsOutputResultSender.SQSOutputSender', function() {
    // Where the mock substitution should occur
    const a = sqsOutputResultSender.SQSOutputSender('a');
    expect(a).toEqual('test');
  })
});

Запуск этого юнит-теста с mocha tests/unit/sqsThingTest.js, однако я получаю: AssertionError: expected undefined to deeply equal 'test'.info: Error AccessDenied: Access to the resource https://sqs.us-east-1.amazonaws.com/ is denied..

Похоже, макет не заменил вызов api aws.Кто-нибудь знает, как я могу высмеять sqs.SendMessage в моем тесте?

Ответы [ 2 ]

0 голосов
/ 19 ноября 2018

Вы можете использовать rewire js - это библиотека, которая позволяет вам вставлять макетированные свойства в ваш модуль, который вы хотите протестировать.

Ваше требование требует выглядеть примерно так:

var rewire = require("rewire");
var sqsOutputResultSender = rewire('../utility/sqsThing');

Rewire позволит вам высмеивать все, что находится в области верхнего уровня вашего sqsThing.js файла.

Также вам нужно вернуть значение sqs.sendMessage, это устранит проблему expected undefined to deeply equal 'test'

Ваш оригинальный файл выглядел бы так же, только с оператором return.

//utility/sqsThing.js
const AWS = require('aws-sdk');
AWS.config.update({ region: 'us-east-1' });
const sqs = new AWS.SQS({ apiVersion: '2012-11-05' });
const outputQueURL = 'https:awsUrl';

const SQSOutputSender = (results) => {
  const params = {
    MessageBody: JSON.stringify(results),
    QueueUrl: outputQueURL,
  };
  // Method that I want to mock
  retun sqs.sendMessage(params, function (err, data) {
    if (err) {
      console.log('Error');
    } else {
      console.log('Success', data.MessageId);
    }
  });
};

Затем вы бы написали свой модульный тест следующим образом:

//sqsThingTest.js
var rewire = require("rewire");
var sqsOutputResultSender = rewire('../utility/sqsThing');
const mochaccino = require('mochaccino');
const { expect } = mochaccino;
const sinon = require('sinon');

describe('SQS thing test', function() {
    beforeEach(function () {
        sqsOutputResultSender.__set__("sqs", {
            sendMessage: function() { return 'test' }
        });
    });

  it('sqsOutputResultSender.SQSOutputSender', function() {
    // Where the mock substitution should occur
    const a = sqsOutputResultSender.SQSOutputSender('a');
    expect(a).toEqual('test');
  })
});

В этом примере возвращается объект со свойством sendMessage, но его можно заменить шпионом.

Rewire Docs

0 голосов
/ 16 ноября 2018

Попробуйте переместить объявление sqsOutputResultSender после того, как заглушите функцию sendmessage

    var sqsOutputResultSender;
    const AWS = require('aws-sdk');
    const sqs = new AWS.SQS({ apiVersion: '2012-11-05' });

    const mochaccino = require('mochaccino');

    const { expect } = mochaccino;
    const sinon = require('sinon');


    describe('SQS thing test', function() {
        beforeEach(function () {
            sinon.stub(sqs, 'sendMessage').callsFake( function() { return 'test' });
            sqsOutputResultSender = require('../utility/sqsThing');
        });

        afterEach(function () {
            sqs.sendMessage.restore();
        });

      it('sqsOutputResultSender.SQSOutputSender', function() {
        // Where the mock substitution should occur
        const a = sqsOutputResultSender.SQSOutputSender('a');
        expect(a).toEqual('test');
      })
    });
...