任何里面的东西then
除非调用承诺回调,否则不会运行 - 这是像您在这里经历的那样存在误报的风险。由于期望从未运行,因此测试将在此处通过。
有很多方法可以确保您不会得到这样的误报。例子:
A) 回报承诺
Jasmine 将等待承诺在超时时间内得到解决。
- 如果不及时解决,测试就会失败。
- 如果承诺被拒绝,测试也会失败。
Beware如果您忘记返回,您的测试将给出假阳性!
describe('test the returned value from the promise', function() {
return $scope.getTheData(someId)
.then(function(result) {
expect(result).toBe('something expected');
});
});
B) 使用done
Jasmine 为测试方法提供的回调
- If
done
在超时时间内未调用测试将失败。
- If
done
使用参数调用测试将失败。
这里的catch会将错误传递给jasmine,你会看到错误
在输出中。
Beware如果您忘记了捕获,您的错误将被吞没,并且您的测试将因通用超时错误而失败。
describe('test the returned value from the promise', function(done) {
$scope.getTheData(someId)
.then(function(result) {
expect(result).toBe('something expected');
done();
})
.catch(done);
});
C) 使用间谍和手动启动(同步测试)
如果您不完美,这可能是编写测试的最安全方法。
it('test the returned value from the promise', function() {
var
data = { data: 'lots of data' },
successSpy = jasmine.createSpy('success'),
failureSpy = jasmine.createSpy('failure');
$scope.getTheData(someId).then(successSpy, failureSpy);
$httpBackend.expect('GET', 'the/url/to/my/data').respond(200, data);
$httpBackend.flush();
expect(successSpy).toHaveBeenCalledWith(data);
expect(failureSpy).not.toHaveBeenCalled();
});
同步测试技巧
当需要让控制器/服务运行时,您可以手动启动 httpBackend、超时和范围更改更进一步. $httpBackend.flush()
, $timeout.flush()
, scope.$apply()
.