The*_*idz 5 service dependencies mocking jasmine angularjs
我是一名新手程序员,对AngularJS和单元测试的实践都很陌生.我花了好几个小时试图找到解决方案,但我变得越来越困惑.如果有人能指出我正确的方向,我会非常感激.我会尝试尽可能具有描述性.
情况是这样的:
我在AngularJS(服务A)中创建了一个具有几个功能的服务.这些函数中的每一个都向REST API发出$ http GET请求,并返回包含JSON数据的$ http promise对象.在这些函数中,URL是通过实现另一个非常简单的服务(服务B)构建的,该服务已作为依赖项注入到服务A中.我创建了一个服务B的模拟,以将其与所有依赖项隔离开来.这两个服务都在名为"services"的同一模块中定义.在这种情况下,没有真正需要这种依赖,但我只想了解它是如何工作的.
使用Jasmine,我想为Service A构建一个单元测试,以确保正确构造它对API的请求,并且可能在返回正确的JSON数据时.同时,我不希望进行任何真正的API调用.
这就是我所知道的:
$ httpBackend mock是我需要能够对API进行虚假调用的,它提供了期望某些请求并返回指定结果的功能.
我需要测试真正的服务A并注入我创建的服务B的模拟.我知道有很多方法可以使用Jasmine Spies和$ provide来实现.我也看过使用sinon.js的例子,我不确定哪种方法最好.
我将在下面发布我的源代码,这是用CoffeeScript编写的.
服务A:
'use strict'
angular.module("services")
.service("ServiceA", ["$http", "ServiceB", ($http, ServiceB) ->
#Uses underscore.js to set this default attribute
defaults = withCredentials:true
getVarset: (itemName, options={}) ->
options.method = "GET"
options.url = ServiceB.makeUrl("item/#{itemName}")
$http _.defaults(options, defaults)
getVarsets: (options = {}) ->
options.method = "GET"
options.url = ServiceB.makeUrl("items")
$http _.defaults(options, defaults)
getModelsForVarset: (itemName, options = {}) ->
options.method = "GET"
options.url = ServiceB.makeUrl("item/#{itemName}/prices")
$http _.defaults(options, defaults)
])
Run Code Online (Sandbox Code Playgroud)
服务B:
'use strict'
angular.module('services')
.service 'ServiceB', [ ->
# Just return the string
# This service builds the real URL, but I've removed this
makeUrl: (Url) ->
"#{Url}"
]
Run Code Online (Sandbox Code Playgroud)
那么你是说你知道如何使用 $provide/Jasmine 间谍来做到这一点并且正在寻找替代方案?我主要使用 $provide/spy 方法进行模拟,到目前为止,它对我来说效果非常好。
就像是:
beforeEach(function() {
// set up a default value for your mock
bMock = {
makeUrl: jasmine.createSpy('makeUrl() mock').andReturn('http://www....')
}
// use the $provide service to replace ServiceB
// with your mock
module('services', function($provide) {
$provide.value('ServiceB', bMock);
});
});
it('should do what its supposed to do', function() {
// test...
});
Run Code Online (Sandbox Code Playgroud)
那么,如果你想使用 $httpBackend 来模拟服务 A 中的 http 请求,你只需要使用 $injector 服务来获取 $httpBackend,然后在其上调用 .when(...) 来进行设置,a la http://docs.angularjs.org/api/ngMock.$httpBackend