I'm trying to get chai-as-promised
to work with $q
promises with karma unit tests.
svc.test = function(foo){
if (!foo){
// return Promise.reject(new Error('foo is required'));
return $q.reject(new Error('foo is required'));
} else {
// get data via ajax here
return $q.resolve({});
}
};
it.only('should error on no foo', function(){
var resolvedValue = MyServices.test();
$rootScope.$apply();
return resolvedValue.should.eventually.be.rejectedWith(TypeError, 'foo is required');
});
The unit test just times out. I am not sure what I'm doing wrong here to get the promise to resolve properly. It seems to be an issue with using $q
-- when I use native Promise.reject()
it works fine.
I filed a ticket here, but nobody seems to be responding: https://github.com/domenic/chai-as-promised/issues/150
The way chai-as-promised
expects to modify promise assertions is transferPromiseness
method.
By default, the promises returned by Chai as Promised's assertions are regular Chai assertion objects, extended with a single then method derived from the input promise. To change this behavior, for instance to output a promise with more useful sugar methods such as are found in most promise libraries, you can override chaiAsPromised.transferPromiseness.
For Angular 1.3+ support, $q
promises can be duck-typed by $$state
property, so native promises won't be affected:
chaiAsPromised.transferPromiseness = function (assertion, promise) {
assertion.then = promise.then.bind(promise);
if (!('$$state' in promise))
return;
inject(function ($rootScope) {
if (!$rootScope.$$phase)
$rootScope.$digest();
});
};
chaiAsPromised
chains each asserted promise with then
. Even if the promise is settled, the rest of the chain still requires the digest to be triggered manually with $rootScope.$digest()
.
As long as the spec contains no asynchronous code, it becomes synchronous, no promise is required to be returned:
it('...', () => {
...
expect(...).to.eventually...;
expect(...).to.eventually...;
});
And is equal to mandatory $rootScope.$digest()
after each set of eventually
assertions/expectation when transferPromiseness
wasn't set:
it('...', () => {
...
expect(...).to.eventually...;
expect(...).to.eventually...;
$rootScope.$digest();
});
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With