2015-01-13 1 views
1

이미 물어 본 question 요점은 터미널에 범위가 없지만 Chrome 디버깅 도구에 존재합니다. 대답에도 불구하고 그것은 고쳐지지 않았다.Jasmine, AngularJs를 사용하여 _.defer()를 테스트하는 방법

질문은 벨로우 명령어, 특히 expect(scope.measurementScroll).toBe(true); 라인을 테스트하는 올바른 구문입니다. 웹을 통해 파고하지만 내 경우에는 밑줄 방법 _.defer()이 어디에서 대부분의 질문이 $q.defer()에 관련된 모든 비슷한 질문을 찾을 수 없습니다

컨트롤러

'use strict'; 
angular.module('myApp') 
    .controller('MeasurementsTimelineCtrl', ['$scope', '$state', 'Measurements', function($scope, $state, Measurements) { 
    $scope.measurements = null; 
    var userId = $scope.currentUser ? $scope.currentUser.id : null; 
    if (userId) { 
     var listOfMeasurements = Measurements.userIndex(userId); 
     listOfMeasurements.then(function(data){ 
     $scope.measurements = data; 
     $scope.$broadcast('measurements-updated', $scope.measurements); 
     }); 
    } 
    }]); 

지침 :

'use strict'; 
angular.module('myApp') 
    .directive('dashboardMeasurementTimeline', ['$window', function($window) { 
    return { 
     restrict: 'E', 
     templateUrl: 'myView.html', 
     controller: 'MeasurementsTimelineCtrl', 
     link: function(scope, element){ 
     scope.$on('measurements-updated', function(measurements) { 
      _.defer(function(){ 
      if(measurements) { 
       scope.measurementScroll = true; 
      } 
      }); 
     }); 
     } 
    }; 
    }]); 

테스트

'use strict'; 
describe('Directive: dashboardMeasurementTimeline', function() { 

    var $rootScope, $compile, element, scope; 

    beforeEach(function() { 
    module('myApp'); 

    inject(function($injector) { 
     $rootScope = $injector.get('$rootScope'); 
     $compile = $injector.get('$compile'); 
    }); 

    scope = $rootScope.$new(); 
    element = angular.element('<dashboard-measurement-timeline></dashboard-measurement-timeline>'); 
    element = $compile(element)(scope); 

    scope.currentUser = {id : 'someId'}; 
    scope.$digest(); 
    scope.measurements = [{id: 'someId', time_of_test: 'Tue, 30 Dec 2014 14:00:00 -0000'}, 
     {id: 'someId', time_of_test: 'Thu, 20 Nov 2014 03:00:00 -0000'},]; 
    scope.$broadcast('measurements-updated', scope.measurements); 
    scope.$apply(); 
    }); 

    it('should assign true value to measurementScroll', function() { 
    expect(scope.measurementScroll).toBe(true); 
    }); 
}); 
+0

재스민 1.3 또는 2.0? – tasseKATT

+0

내가 사용하는 플러그인은'karma-jasmine : 0.1.5'입니다. 인터넷 검색 중에 Jasmine 2.0과 동등하다는 것을 알았습니다. – Max

답변

2

시험에 정의 된 defer 함수를 사용하여 모의 언더 스코어 라이브러리를 주입하여이를 수행 할 수 있습니다. 이 작업을 수행 할 수있는 방법은 다음 쉽게 조롱 할 수있는 자신의 공장, _, 정의하는 것입니다 :이 지침에서 그런

app.factory('_', function($window) { 
    return $window._; 
}); 

을, 당신은 그것을 주입하여 사용할 수 있습니다

app.directive('dashboardMeasurementTimeline', ['_', function(_) { 

에서 테스트, 당신은 다음을 조롱 할 수 있습니다

var deferCallback; 
beforeEach(module(function($provide) { 
    deferCallback = null; 
    $provide.value('_', { 
    defer: function(callback) { 
     deferCallback = callback; 
    } 
    }); 
})); 

이 대신 진짜 하나, 지시어,321에 전달 된 콜백을 저장하는 모의 _, 사용된다는 것을 의미합니다 필요할 때 deferCallback로 0 그래서 당신은 그것을 호출 할 수 있습니다 : 그것은 가능한 한 빨리 테스트를 유지으로

scope.$broadcast('measurements-updated', scope.measurements); 
deferCallback(); 

이것은 보통 done()를 사용하는 것보다 더 나은 생각이다 시험 동기를합니다.

당신은 위의 http://plnkr.co/edit/r7P25jKzEFgE5j10bZgE?p=preview

+0

대단히 감사합니다. @Michal Charezma, 솔루션은 훌륭하고 문제를 해결합니다. – Max

+0

이제는 예를 들어 내가 사용하고있는 것처럼 '_'의 다른 메소드를 사용할 때 에러가 발생합니다 : 'angular.element (scrollContainer) .bind ('scroll', _.throttle (scope.disableButtons, 500)); ' 'throttle()'메소드가 존재하지 않는 것처럼 보입니다 – Max

+1

@Max'$ provide.value'에 전달 된 객체에'throttle'을 추가 할 수 있어야합니다. –

0

@Michal Charezma에서 근무 볼 수 있습니다, 실제로 솔루션 인 문제에 대한 훌륭한 솔루션을 준하지만 알고 보니 그것은 _ 기능의 나머지 부분에 대한 다른 제한 사항이 있습니다. 예 :

angular.element(scrollContainer).bind('scroll', _.throttle(scope.disableButtons, 500)); 

throttle 미정인지 오류 일으킨다.

@ Michal의 논리를 따르면 _.throttle()과 같은 기능을 올바르게 작동시키는 또 다른 해결책을 찾았습니다.같은 사양에서,

app.factory('_', function($window) { 
    return $window._; 
}); 

하나 만 defer 기능을 조롱 할 수 있습니다 : 대신 _를 가져 와서 사용하는 그래서, 당신은 lodash이없는 경우

var deferCallback = $window._.defer.mostRecentCall.args[0]; 
deferCallback() 
+1

이 메소드가 실제로 모의 객체. 나는 그것이 콜백이 두 번, 한 번 강제 될 때까지 콜백이 지연되도록하고, 다른 콜백이 연기 된 콜백에 의해 타임 아웃 된 후에도 발생할 수 있다고 생각한다. –

+0

오, 정말 재밌는 점은 사양을 다시 확인해야한다는 것입니다. 고맙습니다.) – Max

1

서비스는 당신에게 수 주입하기로 그냥 defer 메서드를 통해 스파이가되고, 함수의 실행에 관심이 있다면 callFake을 설정하고 인수 함수를 defer으로 전달하면됩니다.

spyOn(_, 'defer').and.callFake(f => f()); 

더 깊은의 당신이 다음 호출이 있다고 가정 해 봅시다 :

function toTest() { 
_.defer(() => service.callAFunction()); 
} 

다음 테스트에서 당신이 말할 수 :

it('should call service.callAFunction',() => { 
    spyOn(service, 'callAFunction'); 
    spyOn(_, 'defer').and.callFake(f => f()); 
    toTest(); 
    expect(_.defer).toHaveBeenCalled(); 
    expect(service.callAFunction).toHaveBeenCalled(); 
}