Jasmine AngularJS-存储状态/数据的测试工厂
我正在使用遗留API开发新版本的应用程序(我无法控制API返回的内容等) 在app init上,我请求并存储一些站点范围的工厂信息,我称之为Jasmine AngularJS-存储状态/数据的测试工厂,jasmine,mocha.js,karma-runner,karma-jasmine,Jasmine,Mocha.js,Karma Runner,Karma Jasmine,我正在使用遗留API开发新版本的应用程序(我无法控制API返回的内容等) 在app init上,我请求并存储一些站点范围的工厂信息,我称之为stateFactory。在stateFactory中有类别属性(对象数组),它存储id->category name关系 在我的应用程序模板中,我使用一个过滤器,通过id{{cat_id | categoryNameByIdFilter}提取类别的名称,该过滤器正在stateFactory.categories中进行查找,并返回类别名称 我如何为这些功能(
stateFactory
。在stateFactory中有类别
属性(对象数组),它存储id->category name
关系
在我的应用程序模板中,我使用一个过滤器,通过id{{cat_id | categoryNameByIdFilter}
提取类别的名称,该过滤器正在stateFactory.categories
中进行查找,并返回类别名称
我如何为这些功能(茉莉花、摩卡、柴等)编写单元测试?
// represantion of what the stateFactory looks like with some data in it
app.factory('stateFactory', ['', function(){
return {
categories = [
{ cat_id: 1, cat_name: "some category name" },
{ cat_id: 2, cat_name: "another category name" }
];
};
}])
// categoryNameByIdFilter
app.factory('categoryNameByIdFilter', ['stateFactory', function(stateFactiry){
return function(cat_id){
if ( !cat_id ) return null;
var cat_obj = _.findWhere(stateFactiry.categories, {
id: cat_id
});
if ( !cat_obj ) return null;
return cat_obj.cat_name;
};
}]);
我建议用茉莉花和柠檬。您可以创建一个模拟的
状态工厂
,这样在单元测试时它就不会碰到web服务。我曾经创造过我的模拟和间谍。然后,您可以使用模拟而不是实际服务。这样,唯一被测试的系统是类别NameByIdFilter
,而不是您的web服务
// representation of what the stateFactory looks like with some data in it
app.factory('stateFactory', ['', function ()
{
return function ()
{
//This is the real stateFactory, which we are going to mock out.
};
}]);
// categoryNameByIdFilter - The system under test in this example
app.factory('categoryNameByIdFilter', ['stateFactory', '_', function (stateFactiry, _)
{
return function (cat_id)
{
if (!cat_id) return null;
var cat_obj = _.findWhere(stateFactiry.categories, {
id: cat_id
});
if (!cat_obj) return null;
return cat_obj.cat_name;
};
}]);
给定上面的代码,我们可以通过执行以下操作来测试categoryNameByIdFilter
describe("categoryNameByIdFilter", function ()
{
beforeEach(module('YOUR_APP_MODULE'));
beforeEach(function ()
{
//The following line creates a mock of what we expect the state factory to return.
//We're mocking this because it is no the system under test, the filter is.
//A sinon 'stub' is a spy
mockStateFactory = sinon.stub({
categories: [
{ id: 1, cat_name: "some category name" },
{ id: 2, cat_name: "another category name" }
]
});
module(function ($provide)
{
//When Angular asks for a stateFactory, give them this mock instead
$provide.value('stateFactory', mockStateFactory);
});
});
//You can inject a filter using the "inject" method below
it("should filter by id", inject(function (categoryNameByIdFilter)
{
//Wrap categoryNameByIdFilter in a spy so that we can make assertions off of it.
var spy = sinon.spy(categoryNameByIdFilter);
var result = spy(1);
expect(result).toEqual("some category name");
expect(spy.calledBefore(mockStateFactory)).toBeTruthy();
expect(spy.returned("some category name")).toBeTruthy();
sinon.assert.calledOnce(spy);
spy(2);//Returns something besides "some category name"
expect(spy.alwaysReturned("some category name")).not.toBeTruthy();
sinon.assert.calledTwice(spy);
}));
});
那间谍呢?这有什么用吗?仍然不是关于
spy
背后的概念,你可以在这里使用jasmine spy。不过,我建议使用Sinon。这是一个很棒的javascript模拟框架。你想让我用茉莉花或西农间谍重做溶液吗?好的。我们将不胜感激。一些背景故事,为什么和如何也很好。我添加了西农间谍和模拟。您现在可以对categoryNameByIdFilter spy进行断言,查看其行为是否符合您的预期。非常感谢。我听说过西农,但从来没有机会使用它。我会看透你的例子,希望你能理解发生了什么;)谢谢!