Reputation: 430
I use 'redux-actions' and have async action creator in Redux I try to write unit tests, but get an error:
Timeout - Async callback was not invoked within the 100000 ms timeout specified by jest.setTimeout.
Probably this is due to the call of the timer inside my action. How can I fix this error?
actions.js
import axios from 'axios';
import { createAction } from 'redux-actions';
export const loadingNewsRequest = createAction('LOADING_NEWS_REQUEST');
export const loadingNewsSuccess = createAction('LOADING_NEWS_SUCCESS');
export const loadingNewsFailure = createAction('LOADING_NEWS_FAILURE');
const path = 'http://127.0.0.1:7000';
const timeout = 5000;
const loadingTimeout = 60000;
export const loadNews = () => async (dispatch) => {
dispatch(loadingNewsRequest());
try {
const response = await axios.get(`${path}/news`, { timeout });
const timer = setTimeout(() => loadNews()(dispatch), loadingTimeout);
dispatch(loadingNewsSuccess({ allNews: response.data, timer }));
} catch (err) {
const timer = setTimeout(() => loadNews()(dispatch), loadingTimeout);
dispatch(loadingNewsFailure({ err: err.message, timer }));
}
};
actions.test.js
import axios from 'axios';
import MockAdapter from 'axios-mock-adapter';
import configureStore from 'redux-mock-store';
import thunk from 'redux-thunk';
import * as actions from './index';
const middlewares = [thunk];
const mockStore = configureStore(middlewares);
describe('loadNews', () => {
const newsData = [ { x: 1}, { y: 2} ];
it('returns data when sendMessage is called', async (done) => {
const mock = new MockAdapter(axios);
mock.onGet('http://127.0.0.1:7000/news').reply(200, newsData);
jest.setTimeout(100000);
const expectedActions = [
actions.loadingNewsRequest(),
actions.loadingNewsSuccess(
{
allNews: newsData,
timer: 4,
},
),
];
const initialState = { allNews: [], timer: null };
const store = mockStore(initialState);
await store.dispatch(actions.loadNews());
expect(store.getActions()).toEqual(expectedActions);
});
});
Upvotes: 1
Views: 1867
Reputation: 222309
async
function returns a promise that is consumed by Jest. done
callback is a legacy way to write asynchronous tests. It should never be used simultaneously with promises and async
functions.
done
takes priority over a promise in a way Jest handles asynchronous tests. Since done
is never called, it waits for a timeout and fails.
It should be:
it('returns data when sendMessage is called', async () => {
...
100000 is too much for a timeout, if there is asynchronous process, it completes complete within several seconds. 15000 is long enough to make sure a test never completes.
Upvotes: 1