1. prepare fetch module

Let’s implement a simple module that fetches success data from an API and returns the {success: true}.

1
2
3
4
5
6
7
8
// fetchData.js
import axios from "axios";

export const fetchData = (fn) => {
axios.get('http://www.dell-lee.com/reactt/api/demo.json').then(res => {
fn(res.data)
})
}

In the above implementation we expect the fetchData.js module to return a promise. We chain a call to then to receive the data.

2. async function use callback type

1
2
3
4
5
6
7
// fetchData.test.js
import {fetchData} from "./fetchData.js";
test('fetchData return {success: true}', () => {
fetcchData((data) => {
expect(data).toEqual({success: true})
})
})

npm run test
actually it always execute successfully,because it won’t wait the async function finished. we can use done to ensure the test is execute finished.

1
2
3
4
5
6
7
import {fetchData} from "./fetchData.js";
test('fetchData return {success: true}', (done) => {
fetcchData((data) => {
expect(data).toEqual({success: true})
done();
})
})

3. return promise derectly

1
2
3
4
5
6
7
8
9
10
11
12
13
14
// fetchData.js
import axios from "axios";

export const fetchData = () => {
return axios.get('http://www.dell-lee.com/reactt/api/demo.json')
}

// fetchData.test.js
import {fetchData} from "./fetchData.js";
test('fetchData return {success: true}', () => {
return fetcchData().then((res) => {
expect(res.data).toEqual({success: true})
})
})

need to add return

4. Error handling

Errors can be handled using the .catch method. Make sure to add expect.assertions to verify that a certain number of assertions are called. Otherwise a fulfilled promise would not fail the test:

1
2
3
4
5
6
7
8
// fetchData.test.js
test('test fetchData return 404', () => {
// use assertions at least execute the expect method one time
expect.assertions(1)
return fetchData().catch((e) => {
expect(e.toString().indexOf('404') > -1).toBe(true)
})
})

5. use resolves

There is a less verbose way using resolves to unwrap the value of a fulfilled promise together with any other matcher. If the promise is rejected, the assertion will fail.

1
2
3
4
5
6
7
8
// fetchData.test.js
test('test fetchData return { success: true}', () => {
return expect(fetchData()).resloves.toMatchObject({
data: {
success: true
}
})
})

use rejects

The .rejects helper works like the .resolves helper. If the promise is fulfilled, the test will automatically fail.

1
2
3
4
// fetchData.test.js
test('test fetchData return 404', () => {
return expect(fetchData()).rejects.toThrow()
})

async/await

Writing tests using the async/await syntax is easy. Here is how you’d write the same examples from before:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
// fetchData.test.js
test('test fetchData return { success: true}', async () => {
const result = await fetchData();
return expect(result.data).toEqual({success: true})
})

// async/await can also be used with `.resolves`.
it('works with async/await and resolves', async () => {
expect.assertions(1);
await expect(fetchData()).resolves.toEqual({success: true});
});

test('test fetchData return 404', async () => {
expect.assertions(1);
try {
await fetchData();
} catch(e) {
expect(e.toString()).toEqual("Error: Request faild with with status code 404")
}
})