Asynchronous tests

The asynchronous nature of JavaScript—made popular by AJAX and jQuery—has always been one of the draw-cards of the language, and is the principal architecture behind Node-based applications. Let's take a quick look at an asynchronous class, and then describe how we should go about testing it. Consider the following TypeScript code:

class MockAsyncClass { 
    executeSlowFunction(success: (value: string) => void) { 
        setTimeout(() => { 
            success("success"); 
        }, 1000); 
    } 
}

This MockAsyncClass has a single function, named executeSlowFunction, which takes a function callback named success. Within the executeSlowFunction code, we are simulating an asynchronous call with the setTimeout function, and only calling the success callback after 1000 milliseconds (1 second). This function is therefore simulating an asynchronous function, as it will only execute the callback after a full second.

Our test for this executeSlowFunction may appear as follows:

describe("asynchronous tests", () => { 
    it("failing test", () => { 
 
        let mockAsync = new MockAsyncClass(); 
        let returnedValue!: string; 
        console.log(`1. calling executeSlowFunction`); 
        mockAsync.executeSlowFunction((value: string) => { 
            console.log(`2. executeSlowFunction returned`); 
            returnedValue = value; 
        }); 
        console.log(`3. checking returnedValue`); 
        expect(returnedValue).toEqual("success"); 
    }); 
 
}); 

Firstly, we instantiate an instance of the MockAsyncClass, as well as a variable named returnedValue. Note how we need to use the definite assignment operator here (!) to allow the code to compile correctly. We then call executeSlowFunction with an anonymous function for the success parameter. This anonymous function sets the value of returnedValue to whatever was passed in from the MockAsyncClass. Our expectation is that the returnedValue should equal "success", but, if we run this test now, our test will fail with the following error message:

What is happening here, is that because executeSlowFunction is asynchronous, JavaScript will not wait until the callback function is called before executing the next line of code. This can be verified through the use of our console logging statements. Our test execution flow is expected to follow 1, then 2, then 3. If we check the console output of this test, we can see the following:

1. calling executeSlowFunction
3. checking returnedValue

This means that the expectation (at 3) is being called before executeSlowFunction has had a chance to call our anonymous callback function (setting the value of returnedValue). In fact, the entire test has completed before the executeSlowFunction has even had a chance to log anything to the console.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
3.20.238.187