Redux Mock Store
redux-mock-store is a utility package designed to facilitate testing of Redux asynchronous action creators and middleware by providing a mocked Redux store. Its primary function is to capture a log of all dispatched actions, which can then be asserted against in tests. Unlike a real Redux store, `redux-mock-store` does not process actions through reducers, meaning its internal state never updates. This library is currently at version 1.5.5. However, since this version, `redux-mock-store` has been officially deprecated by the Redux team. The recommended testing practice now involves using a real Redux store to test the combined behavior of action creators, reducers, and selectors, asserting on observable state changes rather than just dispatched actions. This package is therefore in a deprecated status, with an implied end of active development and maintenance.
Common errors
-
Expected received actions to equal [...], but actual actions were empty array or incorrect.
cause Actions were dispatched but not captured, often due to improper asynchronous handling or not calling `store.getActions()` after the async operation completes.fixEnsure that `store.dispatch()` for asynchronous actions is `await`ed or returns a Promise, and `store.getActions()` is called *after* the promise resolves. Verify all necessary middlewares (e.g., `redux-thunk`) are correctly configured with `configureStore`. -
TypeError: configureStore is not a function
cause This usually indicates an incorrect import statement, particularly when mixing CommonJS `require` with ESM `import` semantics or attempting to destructure a default export.fixFor ESM, use `import configureStore from 'redux-mock-store'`. For CommonJS, use `const configureStore = require('redux-mock-store').default`.
Warnings
- breaking The `redux-mock-store` package, particularly its `configureStore` method, has been officially deprecated since version 1.5.5 by the Redux team. The recommended testing approach for Redux applications is now to use a real Redux store to verify observable state changes rather than solely focusing on dispatched actions.
- gotcha The `redux-mock-store` intentionally does not run reducers or update its internal state when actions are dispatched. Assertions made on `store.getState()` after dispatching actions will always reflect the `initialState` provided during store creation.
- deprecated The approach of testing Redux logic with a mock store that only captures actions, as offered by `redux-mock-store`, is now considered a suboptimal testing practice by the Redux team. This method can lead to brittle tests and a disconnect from the actual application behavior.
Install
-
npm install redux-mock-store -
yarn add redux-mock-store -
pnpm add redux-mock-store
Imports
- configureStore
const { configureStore } = require('redux-mock-store')import configureStore from 'redux-mock-store'
Quickstart
import configureStore from 'redux-mock-store';
import thunk from 'redux-thunk';
// Mock fetch for demonstration purposes in a Node.js environment
global.fetch = async (url) => {
if (url === '/users.json') {
return {
json: async () => ([{ id: 1, name: 'Test User' }]),
ok: true,
status: 200
};
}
throw new Error('Unknown URL: ' + url);
};
const middlewares = [thunk]; // Add your Redux middleware
const mockStore = configureStore(middlewares);
// Define a simple action creator (would be imported in a real app)
const FETCH_DATA_SUCCESS = 'FETCH_DATA_SUCCESS';
function success(data) {
return {
type: FETCH_DATA_SUCCESS,
payload: data
};
}
// Define an async action creator (e.g., using redux-thunk)
function fetchData() {
return (dispatch) => {
// Simulate an async operation, e.g., an API call
return fetch('/users.json')
.then(response => response.json())
.then(data => dispatch(success(data)));
};
}
// Example test using a common testing framework (like Jest)
describe('redux-mock-store with async actions', () => {
it('should dispatch a success action after fetching data', async () => {
const store = mockStore({}); // Initialize mock store with an empty initial state
// Dispatch the async action and await its completion
await store.dispatch(fetchData());
// Retrieve all dispatched actions from the mock store
const actions = store.getActions();
// Assertions on the dispatched actions
expect(actions.length).toEqual(1);
expect(actions[0].type).toEqual(FETCH_DATA_SUCCESS);
expect(actions[0].payload).toEqual([{ id: 1, name: 'Test User' }]);
console.log('Successfully tested async action dispatch:', actions);
});
});