Jasmine + AngularJS:全局服务导致意外的GET请求

时间:2014-10-05 19:13:06

标签: angularjs unit-testing mocking jasmine angular-translate

我有一个服务$language,它在app config中被调用(所以在每个Spec运行之前)。名为$language.update()的方法会触发$translate.use()(后者会触发$http.get())。这会导致Unexpected request: GET /<lang>/i18n

我已经尝试了一些不同的方法来解决这个问题,但每个问题似乎都会引发一个新问题:

全局模拟$translate服务

// not inside a describe()
beforeEach(function() {
    module(function($provide) {
        $provide.value('$translate', {
            get:         function() { return false; },
            storage:     function() { return false; },
            storageKey:  function() {
                return {
                    get: function() { return false; },
                    set: function() { return false; }
                };
            },
            use:         function() { return false; }
        });
    });
});

但是有些东西试图调用$translate(),所以我尝试让mock成为一个返回一个对象的函数,但这也没有用。

通过$ httpBackend

模拟GET请求
// not inside a describe()
beforeEach(function() {
     // this already existed to avoid another problem caused by $translate
    module('MyApp', function config($translateProvider, $anotherProvider) {
        // …
    });

    // new
    inject(function($httpBackend) {
        $httpBackend.when('GET', '/<lang>/i18n').respond({});
    });
});

然后它抱怨Injector already created, can not register a module!模块注入的顺序似乎并不重要。)

我想全局嘲笑我的$语言服务,但后来我无法在自己的Spec中测试它。

理想情况下,我更喜欢全局模拟$ translate,因为它似乎会导致一个接一个的问题。

1 个答案:

答案 0 :(得分:2)

问题在于$translate是提供者;因此,提供商需要提供$:

// Outside of a describe so it's treated as global
beforeEach(function() {
    module('MyModule', function config($providerA, $provide) {
        // …
        $provide.provider('$translate', function() {
            var store                 = {};
            this.get                  = function() { return false; };
            this.preferredLanguage    = function() { return false; };
            this.storage              = function() { return false; };
            this.translations         = function() { return {}; };

            this.$get = ['$q', function($q) {
                var $translate        = function(key) {
                    var deferred = $q.defer(); deferred.resolve(key); return deferred.promise;
                };

                $translate.addPair    = function(key, val) { store[key] = val; };
                $translate.isPostCompilingEnabled = function() { return false; };
                $translate.preferredLanguage = function() { return false; };
                $translate.storage    = function() { return false; };
                $translate.storageKey = function() { return true; };
                $translate.use        = function() { return false; };

                return $translate;
            }];
        });
    });
});