2013-10-24 45 views
21

我正在使用AngularJS的v1.2.0-rc.3與Jasmine測試框架。如何用Jasmine測試一個AngularJS控制器,該控制器調用返回承諾的服務方法

我想斷言控制器調用服務方法。服務方法返回一個承諾。控制器看起來像這樣:

angular.module('test', []) 
.controller('ctrl', ['$scope', 'svc', function ($scope, svc) { 
    $scope.data = []; 
    svc.query() 
    .then(function (data) { 
    $scope.data = data; 
    }); 
}]); 

我想測試,當服務方法的延期解析時,數據分配給範圍。我創建了一個模擬的服務和單元測試是這樣的:

describe('ctrl', function() { 
    var ctrl, scope, svc, def, data = [{name: 'test'}]; 
    beforeEach(module('test')); 
    beforeEach(inject(function($controller, $rootScope, $q) { 
    svc = { 
     query: function() { 
     def = $q.defer(); 
     return def.promise; 
     } 
    }; 
    scope = $rootScope.$new(); 
    controller = $controller('ctrl', { 
     $scope: scope, 
     svc: svc 
    }); 
    })); 
    it('should assign data to scope', function() { 
    spyOn(svc, 'query').andCallThrough(); 
    deferred.resolve(data); 
    scope.$digest(); 
    expect(svc.query).toHaveBeenCalled(); 
    expect(scope.data).toBe(data); 
    }); 
}); 

我預計SVC的查詢方法被調用,但顯然還沒有。

我跟着this指南嘲笑單元測試的承諾。

我在做什麼錯?

回答

28

看來我把我的間諜放在了錯誤的地方。當我把它放在beforeEach時,測試通過。

beforeEach(inject(function($controller, $rootScope, $q) { 
    svc = { 
     query: function() { 
     def = $q.defer(); 
     return def.promise; 
     } 
    }; 
    spyOn(svc, 'query').andCallThrough(); 
    scope = $rootScope.$new(); 
    controller = $controller('ctrl', { 
     $scope: scope, 
     svc: svc 
    }); 
    })); 
+2

尤其要注意spyOn()結束時的'andCallThrough'調用。 –

+0

您的控制器在實例化時調用服務方法,因此您必須在$ controller調用之前監視該服務方法。 – Richard

+0

你能展示完整的工作示例嗎?我無法讓這件事情起作用! :/ 我已經嘗試了很多與上述不同的事情,但一切都返回undefined – SinSync

相關問題