2013-10-09 58 views
13

我有一個控制器從$scope獲取一個值,並將其發送到不同的狀態:測試angularjs UI路由器go()方法

controllers.controller('SearchController', ['$scope', '$state', '$stateParams', 
function($scope, $state, $stateParams) { 
    $scope.search = function() { 
     $stateParams.query = $scope.keyword; 
     $state.go('search', $stateParams); 
    }; 
}]); 

我不確定如何去單元測試這個搜索方法。我該如何驗證go方法是否已被調用,或者使用Karma/AngularJS做某種when($state.go('search', $stateParams)).then(called = true);

回答

31

這些都聽起來像你可以用茉莉花間諜做的事情。

describe('my unit tests', function() { 
    beforeEach(inject(function($state) { 
     spyOn($state, 'go'); 
     // or 
     spyOn($state, 'go').andCallFake(function(state, params) { 
      // This replaces the 'go' functionality for the duration of your test 
     }); 
    })); 

    it('should test something', inject(function($state){ 
     // Call something that eventually hits $state.go 
     expect($state.go).toHaveBeenCalled(); 
     expect($state.go).toHaveBeenCalledWith(expectedState, expectedParams); 
     // ... 
    })); 
}); 

這是一個很好的間諜的cheatsheet這裏http://tobyho.com/2011/12/15/jasmine-spy-cheatsheet/或實際茉莉花文檔here

使用間諜的好處是,它可以讓你避免實際執行狀態轉換,除非你明確告訴它。如果它改變了URL,狀態轉換將會失敗你在Karma的單元測試。

+0

完美,正是我所期待的。 – shmish111

+8

使用Jasmine 2.x,用'.and.callFake'替換函數調用'.andCallFake'。 – satJ