我正在尝试测试依赖于其他服务documentViewer
authService
angular
.module('someModule')
.service('documentViewer', DocumentViewer);
/* @ngInject */
function DocumentViewer($q, authService) {
// ...
this.view = function(doc) {
//...
}
}
这是我的测试目前的样子
it('test', inject(function($q) {
var doc = {
view: function() {
return $q.resolve(0);
}
};
var auth = {
refreshProfileData: function() {
return $q.resolve(0);
},
};
var viewer = createViewer(auth);
}));
function createViewer(auth) {
var viewer;
module({
authService: auth
});
inject(function(documentViewer) {
viewer = documentViewer;
});
return viewer;
}
问题是,我需要致电inject
来抓取$q
,然后用它来创建我的模拟,使用module
注册我的模拟,然后调用inject
再次抓住被测单位。
这导致
错误:注射器已经创建,无法注册模块!在bower_components / angular-mocks / angular-mocks.js(第2278行)
我在这里看到了许多答案,说你不能在module
之后拨打inject
,但他们不提供上述场景的替代方案。
这里的正确方法是什么?
PS:我想避免使用beforeEach
,我希望每个测试都是自包含的。
答案 0 :(得分:2)
module
用于定义将使用inject
加载哪些模块,并且在inject
之后无法调用,这是鸡蛋情况。
module
接受的对象用于定义模拟服务with $provide.value
:
如果传递了一个对象文字,则每个键值对将通过$ provide.value在模块上注册,该键是与注入器上的值关联的字符串名称(或标记)。
createViewer
调用module
和inject
的函数不能超过1个。如果这意味着这种自包含的测试是反模式,那么就没有什么可以做的。角度测试最适合通常的习惯,包括beforeEach
和局部变量。
为了消除对$q
的依赖,可以将模拟服务设为factory
。
it('test', function () {
var authFactory = function ($q) {
return {
refreshProfileData: function() {
return $q.resolve(0);
},
};
};
// mocks defined first
module(function ($provide) {
$provide.factory('authService': authFactory);
});
var viewer;
inject(function(documentViewer) {
viewer = documentViewer;
});
// no module(...) is allowed after this point
var $q;
inject(function(_$q_) {
$q = _$q_;
});
var doc = {
view: function() {
return $q.resolve(0);
}
};
});