Friday, January 25, 2019

How to test a Javascript async function returning a promise with Jest

Overview 

Testing JavaScript asynchronous function with Jest.
Reminders:

  • A JavaScript asynchronous function always return a promise
  • When an JavaScript asynchronous function throw an exception, the function really return a rejected Promise with a value.
  • The Jest test must also be asynchronous
  • As 02/2019 Jest cannot test for custom exception thrown. 


The code

/////////////////////////////////////////////////////////
/// An async function that may throw an exception
export const anAsyncFuncThatThrow = async (fail) => { // Javascript async function always return a Promise
     
    if(fail) 
        throw new Error('an error occured'); // Will return a Promise that is rejected with the error as value 
    
    return new Promise(function(resolve, reject) {
        setTimeout( () => {
        resolve("ok"); // Will return a Promise that is resolved/successful with "ok" as the value
        }, 400);
    });
}

/////////////////////////////////////////////////////////
/// An async function that may resolve or reject the returned promise
export const anAsyncFunc = async (rejectPromise) => { // Javascript async function always return a Promise

    return new Promise(function(resolve, reject) {
        setTimeout( () => {
            if(rejectPromise)
                reject('ko');  // Will return a Promise that is rejected with "ko" as the value
            else
                resolve("ok"); // Will return a Promise that is resolved/successful with "ok" as the value
        }, 400);
    });
}

The tests

  


import { anAsyncFuncThatThrow, anAsyncFunc }  from './p';

describe('anAsyncFuncThatThrow', () => {
 
    it('anAsyncFuncThatThrow succeed', async () => { // <= Do not forget the async keyword for the test
    
        const throwException = false;
        await expect( anAsyncFuncThatThrow(throwException) ).resolves.toEqual('ok'); // expect must be preceded by await
    });
    
    it('anAsyncFuncThatThrow throw', async () => { // <= Do not forget the async keyword for the test
    
        const throwException = true;
        await expect( anAsyncFuncThatThrow(throwException) ).rejects.toThrow(Error); // expect must be preceded by await
    });
    
    it('anAsyncFuncThatThrow throw check error message', async () => { // <= Do not forget the async key work for the test
    
        const throwException = true;
        await expect( anAsyncFuncThatThrow(throwException) ).rejects.toThrow('an error occured'); // expect must be preceded by await
    });
 });

describe('anAsyncFunc', () => {
 
    it('anAsyncFunc succeed', async () => { // <= Do not forget the async keyword for the test
    
        const reject = false;
        await expect( anAsyncFunc(reject) ).resolves.toEqual('ok'); // expect must be preceded by await
    });
    it('anAsyncFunc failed/rejcted', async () => { // <= Do not forget the async keyword for the test
    
        const reject = true;
        await expect( anAsyncFunc(reject) ).rejects.toEqual('ko'); // expect must be preceded by await
    });
});


No comments:

Post a Comment