【问题标题】:AngularJS, Mocha, Chai: testing service with promisesAngularJS、Mocha、Chai:用 Promise 测试服务
【发布时间】:2015-10-23 11:44:22
【问题描述】:

我发现了几篇将这段代码作为异步单元测试方式的帖子:

服务:

angular.module('miservices', [])
.service('myAppServices', ['$http', 'httpcalls', function($http, httpcalls) {
    this.getAccountType = function(){
        return httpcalls.doGet('http://localhost:3010/...').then(function(data){
            return data;
        }, function(error){
            ...
        });
    };
    ...

测试:

describe('testing myAppServices', function(){

beforeEach(module('smsApp'));
it('should handle names correctly', inject(function(myAppServices){
  myAppServices.getAccountType()
  .then(function(data) {
      expect(data).equal({...});
});
...

我们正在使用 AngularJS、Mocha、Chai 并且我们已经安装了 Sinon。

测试永远不会到达.then 部分,但为什么呢?

谢谢!

【问题讨论】:

  • 问题不是promise,而是$http。你必须模拟请求,但你不这样做。
  • 你的意思是httpBackend他们吗?
  • 没错。如果 doGet 和 getAccountType 对实际的 http 响应没有任何作用,您可以跳过此规范并模拟 getAccountType 以获取其他规范。
  • 谢谢@estus!最后一个问题:如果我们确实需要测试来自后端的真实响应怎么办?
  • 保存它以供 e2e 使用,这就是要在那里测试的内容。

标签: angularjs testing mocha.js karma-runner chai


【解决方案1】:

如果您正在测试您的服务,我建议您模拟您的“httpcalls”服务(因为这超出了本测试的范围)。

要模拟它,您可以有多种方法,一种方法是拥有一个仅用于单元测试的模拟模块。

 angular.module('miservices.mocks', [])
.service('httpcalls', ['$q', function($q) {
    this.returnGet = '';
    this.doGet = function(url) {
           return $q.when(this.returnGet);
        };
    };

然后您的单元测试将类似于:

describe('testing myAppServices', function(){

beforeEach(function() {
module('smsApp');
module('miservices.mocks');
});
it('should handle names correctly', inject(function(myAppServices, httpcalls){
  httpcalls.returnGet = 'return data';
  myAppServices.getAccountType()
  .then(function(data) {
      expect(data).equal('return data');
});
...

因为我们在应用程序模块之后插入了 mocks 模块,httpcalls 服务会被它的 mock 版本覆盖,并允许我们正确地测试 myAppServices 而无需进一步的依赖。

【讨论】:

  • 谢谢@pedromarce,我试试看
猜你喜欢
  • 2015-12-01
  • 2019-02-04
  • 1970-01-01
  • 2014-12-21
  • 1970-01-01
  • 2021-11-22
  • 2019-09-15
  • 1970-01-01
相关资源
最近更新 更多