Поставщик Spyon на этапе настройки в приложении angular.js

Я пишу модульные тесты для приложения Angular.js (с karma и jasmine) и хочу проверить определенное поведение модуля на этапе CONFIG. Я хотел бы подтвердить, что вызывается определенная функция ПРОВАЙДЕРА. Я думал, что смогу сделать это с помощью шпионажа на методе провайдера, но получить доступ к провайдеру до того, как «ожидается», оказалось довольно сложно. Вот пример кода:

Код модуля (тестируется)

var myApp = angular.module('myApp', ['restangular']);
myApp.config(['RestangularProvider', function (RestangularProvider) {
    RestangularProvider.setBaseUrl('http://someurl:someport/');
}]);

Я пробовал различные решения, чтобы получить ссылку на RestangularProvider и применить к нему шпиона, но все потерпело неудачу. Самое близкое, что я смог получить, это код ниже:

Код модульного теста

describe("Test if setBaseUrl was called", function () {
    var RestangularProvider;
    beforeEach(module('myApp', function(_RestangularProvider_) {
        RestangularProvider = _RestangularProvider_;
        spyOn(RestangularProvider, "setBaseUrl").and.callThrough();
    }));

    it("should call setBaseUrl.", function() {
        expect(RestangularProvider.setBaseUrl).toHaveBeenCalled();
    });
});

На самом деле я получаю ссылку на RestangularProvider, но перед этим вызывается функция «config» модуля, поэтому я думаю, что шпион не настроен.

Я нашел сообщение, в котором автор решил аналогичную ситуацию с «обходным решением», протестировав настроенную «службу» вместо тестирования фактического вызова метода провайдера. В приведенном выше примере я бы проверил Restangular.configuration.baseUrl в своем ожидании вместо проверки фактического вызова метода setBaseUrl провайдера, но мне показалось, что в определенных ситуациях этого будет недостаточно.

Я новичок в Angular.js, так что это может быть просто случай полного невежества во всей «этапе тестирования конфигурации», поэтому, если это так, пожалуйста, не стесняйтесь меня прямо :]

Любые предложения, критика или указатели?


person raul    schedule 01.07.2014    source источник


Ответы (2)


В конце концов я решил проблему, выделив модуль, за провайдером которого я хотел следить, в другой блок «beforeEach». Измененный код приведен ниже, но я все же был бы признателен за любые комментарии относительно общей идеи о том, действительно ли это «адекватный тест».

describe("Test if setBaseUrl was called", function () {
    var RestangularProvider;
    //Setup the spy.
    beforeEach(function () {

      module("restangular", function(_RestangularProvider_) {
        RestangularProvider = _RestangularProvider_;
        spyOn(_RestangularProvider_, 'setBaseUrl').and.callThrough();
      });
    });

    beforeEach(module('myApp'));

    it("should call setBaseUrl.", function() {
        expect(RestangularProvider.setBaseUrl).toHaveBeenCalled();
    });
});
person raul    schedule 02.07.2014

Как описано выше в OP, вам нужно получить провайдера перед вызовом модуля, который вы хотите протестировать.
Однако нет необходимости разделять его на два блока beforeEach. Вы также должны вызвать функцию inject() (даже если вам нечего вводить) в конце блока beforeEach.

describe('Test if setBaseUrl was called', function () {
  var RestangularProvider;
  //Setup the spy.
  beforeEach(function () {

    module('restangular', function(_RestangularProvider_) {
      RestangularProvider = _RestangularProvider_;
      spyOn(_RestangularProvider_, 'setBaseUrl').and.callThrough();
    });

    module('myApp');

    inject();
  });

  it('should call setBaseUrl.', function() {
    expect(RestangularProvider.setBaseUrl).toHaveBeenCalled();
  });
});

Источник: http://java.dzone.com/articles/unit-testing-config-and-run

person xdmnl    schedule 11.02.2015