javascript - 在被测试的方法中模拟一个函数

标签 javascript node.js unit-testing testing mocking

我想在我的代码中测试一个执行一组不同函数的方法...其中一个内部函数在被调用时会发送一封电子邮件。

我想要的是避免此函数在运行测试时发送电子邮件。有没有办法做到这一点?

我想在我的代码中避开类似下面的东西:

if (app.get('env') !== 'test')

我使用Promises,我要测试的函数如下所示:

var emailService = require('../path/to/custom/service.js');

// This is the method I want to test
exports.sendKeyByEmail = function(email) {
  return _getByEmail(email) // finds a user given an email
    .then(function(user) {
      if (!user) {
        throw new UserNotFoundError();
      }
      user.key = _generateKey(); // generates a random hash
      return user.save(); // saves the user (mongoose stuff...)
    })
    .then(function(user) {
      // This is what I would like to mock during testing
      return emailService.sendKey(user.email, user.key);
    });
}

emailService.sendKey() 方法是发送电子邮件并返回 Promise 的方法。在测试期间,我希望它直接返回已完成的 Promise Promise.resolve(),而不是真正发送电子邮件。

最佳答案

I answered a question just like this yesterday :与其将这两个关注点合并到一个私有(private)方法或隐藏函数中,不如将它们分成两个类并将电子邮件实现传递到外部类中。这将允许您在测试期间提供模拟 emailService 并非常巧妙地解决您的问题。

在设置时,我是构造函数依赖注入(inject)的粉丝,因为它为您提供了 DI 的好处,而无需做任何棘手的事情(如反射)。使用 ES6 参数,您还可以在不模拟任何内容时提供默认值。

非常粗略地说,你可以这样做:

var defaultEmailService = require('../path/to/custom/service.js');

// This is the method I want to test
exports.sendKeyByEmail = function(email, emailService = defaultEmailService) {
  return _getByEmail(email) // finds a user given an email
    .then(function(user) {
      if (!user) {
        throw new UserNotFoundError();
      }
      user.key = _generateKey(); // generates a random hash
      return user.save(); // saves the user (mongoose stuff...)
    })
    .then(function(user) {
      // This is what I would like to mock during testing
      return emailService.sendKey(user.email, user.key);
    });
}

在您的测试中,只需传递一个模拟 emailService 即可返回可预测的结果,而无需接触网络。

关于javascript - 在被测试的方法中模拟一个函数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36065899/

相关文章:

unit-testing - Gallio:无法运行测试,因为未找到 MSTest 可执行文件

javascript - Autodesk Viewer 中出现 webGL 错误

javascript - 需要在按钮上单击两次或更多次才能触发功能

javascript - 更新子文档 Mongoose 中的字段

node.js - 从服务器端错误地处理多次点击

Node.js tcp套接字断开连接处理

javascript - 如何使用 coap.registerOption 注册新选项

ruby-on-rails - 在 Controller 中使用 using 方法测试辅助方法

unit-testing - 需要帮助测试 Windows Phone 8 中的绑定(bind)

javascript - jquery "empty"改变滚动条