我有以下代码:
$scope.deleteJob = function(job) {
SandboxService.deleteJob(job.id).then(res => {
if (res.status == 200) {
ngToast.success();
$scope.refreshApps();
}
else {
ngToast.danger();
}
});
};
以及以下单元测试:
it('should show success toast on delete and refresh apps', () => {
spyOn(sandboxService, 'deleteJob').and.returnValue(Promise.resolve({status: 500}));
spyOn(ngToast, 'success');
spyOn(scope, 'refreshApps');
let mockJob = {
'id': 1
};
scope.deleteJob(mockJob);
sandboxService.deleteJob().then(() => {
expect(ngToast.success).toHaveBeenCalled();
expect(scope.refreshApps).toHaveBeenCalled();
});
});
基本上,在删除作业时,如果删除成功且返回状态为200,则显示成功吐司和刷新,否则显示危险吐司。
我希望测试失败,因为它返回状态500,但通过了。这意味着ngToast.success()
和scope.refreshApps()
已被调用。
我在代码中添加了一些日志,它确实返回了status: 500
并进入了else
块。
我在这里想念什么?
答案 0 :(得分:1)
该问题与deleteJob
的异步性质有关。您的it
测试甚至在执行expect
之前就结束了。因此,您需要某种同步。基本上可以使用fakeAsync
中的tick
和@angular/core/testing
来完成。
it('should show success toast on delete and refresh apps', fakeAsync(() => {
...
sandboxService.deleteJob();
tick();
expect(ngToast.success).toHaveBeenCalled();
expect(scope.refreshApps).toHaveBeenCalled();
}));
但是问题是,您用下面的间谍程序覆盖了deleteJob
的原始行为,因此将不会调用ngToast.success
和scope.refreshApps
并且测试将失败。
spyOn(sandboxService, 'deleteJob').and.returnValue(Promise.resolve({status: 500}));
答案 1 :(得分:0)
@uminder的回答指出,由于异步特性,在expect
函数被调用之前,测试已经完成-通过在测试内部添加一些日志来验证。
解决方案是在测试完成时向测试添加一个参数:https://jasmine.github.io/2.0/introduction.html#section-Asynchronous_Support
it('should show success toast on delete and refresh apps', (done) => {
spyOn(sandboxService, 'deleteJob').and.returnValue(Promise.resolve({status: 200}));
spyOn(ngToast, 'success');
spyOn(scope, 'refreshApps');
let mockJob = {
'id': 1
};
scope.deleteJob(mockJob);
sandboxService.deleteJob().then(() => {
expect(ngToast.success).toHaveBeenCalled();
expect(scope.refreshApps).toHaveBeenCalled();
done();
});
});