My unit test code is like this:
// function for my unit test to test exception
const mockServiceThrow = async () => { throw new Error('unit test error message'); };
const createContextAndDoc = () => new Promise((resolve, reject) => {
(async () => {
const res = await mockServiceThrow();
if (res === 1) resolve(1)
else reject(0);
})();
});
createContextAndDoc().catch((e) => {
console.log('--------');
console.log(e.message);
console.log('--------');
});
When i run this unit test:
./node_modules/.bin/jest local_modules/__test__/unhandledException.test.js
The complete output is like this:
RUNS local_modules/__test__/unhandledException.test.js
node:internal/process/promises:246
triggerUncaughtException(err, true /* fromPromise */);
^
[UnhandledPromiseRejection: This error originated either by throwing inside of an async function without a catch block, or by rejecting a promise which was not handled with .catch(). The promise rejected with the reason "Error: unit test error message".] {
code: 'ERR_UNHANDLED_REJECTION'
}
Don't see why it says unhandled, i do have .catch(). Any suggestions ?
Looks like you're invoking the async function right away, which causes the unit test error, and that is never caught since the promise is never returned - so the .catch is not catching anything. The error is not part of the promise chain.
If you want to invoke the function right away you need to catch the error and reject it so the promise finishes.
const mockServiceThrow = async () => { throw new Error('unit test error message'); };
const createContextAndDoc = () => new Promise((resolve, reject) => {
(async () => {
try {
const res = await mockServiceThrow();
if (res === 1) resolve(1)
else reject(0);
} catch (e) {
reject(e)
}
})();
});
createContextAndDoc().catch(e => {
console.log('------------------');
console.log(e.message);
console.log('--------')
})
You could also simplify your code a little:
const mockServiceThrow = async () => { throw new Error('unit test error message'); };
const createContextAndDoc = async () => {
const res = await mockServiceThrow();
if(res === 1) {
return Promise.resolve(1)
} else {
return Promise.reject(0);
}
};
createContextAndDoc().catch(e => {
console.log('------------------');
console.log(e.message);
console.log('--------')
})
Edit: Further explanation of promises.
createContextAndDoc is a function that returns a promise. That promise resolves if res === 1 but rejects if res is something else. For that to happen the mockServiceThrow promised must be resolved. Otherwise you won't get any value for res variable.If that happens then your promise function never fulfills (resolves or rejects).
In your case mockServiceThrow fails and throws an error, this error is not part of the promise you created with new Promis. To make sure your promise fulfilled (resolves or rejects) you need the callbacks, otherwise the error is not part of the promise.
The simplified code has one async function so that when mockServiceThrow fails its part of the async function that you're trying to catch.