Jest Mock功能?

时间:2017-03-29 05:12:23

标签: unit-testing email jestjs

刚开始使用jest,文档在模拟方面似乎不太清楚。

我有一个带有以下代码的模块。如果我想测试发送邮件功能,但不通过mailgun发送实际的电子邮件,我需要在这做什么?我认为在我的测试文件中我需要使用模拟行为,但无法确定如何专门阻止邮件发出,同时还能够检查正确的路由,例如,无效的电子邮件地址,错误抛出等。我是否需要进一步打破此功能?

const Mailgun = require('machinepack-mailgun');
const Emailaddresses = require('machinepack-emailaddresses');
const config = require('../Config');


// Function to send an email
const sendEmail = function (toaddress, toname, sub, msg, cb) {
// Validate the email address is correct and if so send an email. Otherwise log the error and exit.
  Emailaddresses.validate({
    string: toaddress,
  }).exec({
    error(err) {
      return cb(err, null);
    },
    invalid() {
      return cb(new Error('Email address is not valid.'), null);
    },
    success() {
      Mailgun.sendPlaintextEmail({
        apiKey: config.sender.apiKey,
        domain: config.sender.domain,
        toEmail: toaddress,
        toName: toname,
        subject: sub,
        message: msg,
        fromEmail: config.sender.fromEmail,
        fromName: config.sender.fromName,
      }).exec({
        error(err) {
          return cb(err, null);
        },
        success() {
          return cb(null, 'Email Sent.');
        },
      });
    },
  });
};

module.exports.sendEmail = sendEmail;

1 个答案:

答案 0 :(得分:2)

您可以使用自己的实现模拟Mailgun

const Mailgun = require('machinepack-mailgun');
jest.mock('machinepack-mailgun', () = > ({
  sendPlaintextEmail: jest.fn()
}))
it('sends mail and fail', () = > {
  // no add the way `sendPlaintextEmail` should react.
  // in this case return `exec` which always run the `error` part
  Mailgun.sendPlaintextEmail.mockImplementation(() = > ({
    exec: (arg) = > {
      arg.error('someError')
    }
  }))
  const cb = jest.fn()
  sendEmail ('toaddress', 'toname', 'sub', 'msg', cb) 
  expect(Mailgun.sendPlaintextEmail).toHaveBeenCalledWith(...)
  expect(cb).toHaveBeenCalledWith(...)
})

在上面的例子中,我们模拟了mailgun模块,以便sendPlaintextEmail是间谍。然后我们将模块导入到我们的测试中,这样我们就可以在每个测试中设置spy的模拟实现。在示例中,我们设置了行为,以便它返回exec方法,然后由您的代码使用error / success对象调用该方法。然后模拟调用error部分。之后,您可以首先使用正确的参数测试Mailgun.sendPlaintextEmail,然后您可以使用cb"someError"测试null

在另一项测试中,您只需设置exec的行为,即可调用success方法。