茉莉花:测试一个函数,使用茉莉花从不同的函数调用
Jasmine: Testing a function, being called from a different function using jasmine
我在 javascript 文件中有一个方法。
function foo() {
setTimeout(function() {
bar.getSomeUrl();
},WAIT_FOR_SOMETIME);
}
现在getSomeUrl()
实现如下。
var bar = {
getSomeUrl : function(){
window.location.href = 'someUrl';
return;
},
anotherProp : function() {
return bar.getSomeUrl();
}
};
我正在尝试测试当我调用 foo()
方法时是否会调用 getSomeUrl()
方法。
我正在使用 jasmine 进行测试。我的茉莉花测试如下:
describe('This tests getSomeUrl()', function() {
it('is called when foo() is called', function(){
spyOn(bar,'getSomeUrl').and.callFake(function(){});
window.foo();
expect(bar.getSomeUrl).toHaveBeenCalled();
});
});
我真的不关心测试 getSomeUrl()
内部发生的事情,因为我有一个单独的测试。
我想测试的是,当我从某个地方调用我的 foo() 时,getSomeUrl()
被调用。
我有以下问题:
- 如果我这样做,测试会失败,并且在 运行 所有测试结束时,浏览器会重定向到
someUrl
。我没想到会发生这种情况,因为我认为既然我在 bar.getSomeUrl()
上有一个间谍并且正在返回一个 fake method
它实际上不会在我调用 [=23] 时调用 bar.getSomeUrl()
=].
所以我想也许我应该按如下方式进行:
期待(window.foo).toHaveBeenCalled();
这没有意义,因为我正在尝试测试是否正在调用 bar.getSomeUrl()
。
然而,当我这样做时,测试失败并且出现以下错误:
Error: Expected a spy, but got Function.
我还认为可能是 setTimeout
函数导致了问题,并将 foo()
函数更改为:
function foo() {
bar.getSomeUrl();
};
没有改变任何东西
我与 Jasmine 和 Javascript 一起工作才几天,对事情的运作方式有广泛的了解。
非常感谢任何使此测试通过的建议以及关于我做错了什么的指示。
首先,bar.getSomeUrl
应该是一个函数,而不是一个(无效的)对象
var bar = {
getSomeUrl : function() {
window.location.href = 'someUrl';
return;
},
anotherProp : function() {
return bar.getSomeUrl();
}
};
其次,在测试带有超时的代码时使用Jasmine Clock。
describe('This tests getSomeUrl()', function() {
beforeEach(function() {
jasmine.clock().install();
});
afterEach(function() {
jasmine.clock().uninstall();
});
it('is called when foo() is called', function(){
spyOn(bar,'getSomeUrl').and.callFake(function(){});
foo();
expect(bar.getSomeUrl).not.toHaveBeenCalled();
jasmine.clock().tick(WAIT_FOR_SOMETIME);
expect(bar.getSomeUrl).toHaveBeenCalled();
});
});
我在 javascript 文件中有一个方法。
function foo() {
setTimeout(function() {
bar.getSomeUrl();
},WAIT_FOR_SOMETIME);
}
现在getSomeUrl()
实现如下。
var bar = {
getSomeUrl : function(){
window.location.href = 'someUrl';
return;
},
anotherProp : function() {
return bar.getSomeUrl();
}
};
我正在尝试测试当我调用 foo()
方法时是否会调用 getSomeUrl()
方法。
我正在使用 jasmine 进行测试。我的茉莉花测试如下:
describe('This tests getSomeUrl()', function() {
it('is called when foo() is called', function(){
spyOn(bar,'getSomeUrl').and.callFake(function(){});
window.foo();
expect(bar.getSomeUrl).toHaveBeenCalled();
});
});
我真的不关心测试 getSomeUrl()
内部发生的事情,因为我有一个单独的测试。
我想测试的是,当我从某个地方调用我的 foo() 时,getSomeUrl()
被调用。
我有以下问题:
- 如果我这样做,测试会失败,并且在 运行 所有测试结束时,浏览器会重定向到
someUrl
。我没想到会发生这种情况,因为我认为既然我在bar.getSomeUrl()
上有一个间谍并且正在返回一个fake method
它实际上不会在我调用 [=23] 时调用bar.getSomeUrl()
=]. 所以我想也许我应该按如下方式进行:
期待(window.foo).toHaveBeenCalled();
这没有意义,因为我正在尝试测试是否正在调用 bar.getSomeUrl()
。
然而,当我这样做时,测试失败并且出现以下错误:
Error: Expected a spy, but got Function.
我还认为可能是 setTimeout
函数导致了问题,并将 foo()
函数更改为:
function foo() {
bar.getSomeUrl();
};
没有改变任何东西
我与 Jasmine 和 Javascript 一起工作才几天,对事情的运作方式有广泛的了解。
非常感谢任何使此测试通过的建议以及关于我做错了什么的指示。
首先,bar.getSomeUrl
应该是一个函数,而不是一个(无效的)对象
var bar = {
getSomeUrl : function() {
window.location.href = 'someUrl';
return;
},
anotherProp : function() {
return bar.getSomeUrl();
}
};
其次,在测试带有超时的代码时使用Jasmine Clock。
describe('This tests getSomeUrl()', function() {
beforeEach(function() {
jasmine.clock().install();
});
afterEach(function() {
jasmine.clock().uninstall();
});
it('is called when foo() is called', function(){
spyOn(bar,'getSomeUrl').and.callFake(function(){});
foo();
expect(bar.getSomeUrl).not.toHaveBeenCalled();
jasmine.clock().tick(WAIT_FOR_SOMETIME);
expect(bar.getSomeUrl).toHaveBeenCalled();
});
});