Home > Blockchain >  Typing dispatch on a redux store correctly when using multiple middleware
Typing dispatch on a redux store correctly when using multiple middleware

Time:11-08

I'm attempting to configure the dispatch type on a redux store that is using thunk middleware and an optional middleware logger (redux-logger).

This correctly infers the thunk type on store's dispatch...

import { createStore, applyMiddleware } from 'redux';
import thunk, { ThunkMiddleware } from 'redux-thunk';

// ...

const preloadedState = undefined;
export const store = createStore(rootReducer, preloadedState, applyMiddleware(thunk as ThunkMiddleware));

enter image description here

When I expand the middleware to include a conditional logger and spread an array of middleware into applyMiddleware, the store's dispatch is not correctly inferred.


import { createStore, applyMiddleware, Middleware } from 'redux';
import thunk, { ThunkMiddleware } from 'redux-thunk';
import { createLogger } from 'redux-logger';

// ...

const middleware: Middleware[] = [thunk as ThunkMiddleware];

if (Settings.environment === 'development') {
  const logger = createLogger({ collapsed: (_getState, _action, logEntry) => !logEntry.error });
  middleware.push(logger);
}

const preloadedState = undefined;
export const store = createStore(rootReducer, preloadedState, applyMiddleware(...middleware));

enter image description here

This is driving me crazy, any thoughts as to how to fix the typing issue when spreading the middleware array?

CodePudding user response:

This is where redux-toolkit comes in real handy.

Their docs mention to do it this way

import { configureStore } from '@reduxjs/toolkit'
import { useDispatch } from 'react-redux'
import rootReducer from './rootReducer'

const store = configureStore({
  reducer: rootReducer,
})

export type AppDispatch = typeof store.dispatch
export const useAppDispatch = () => useDispatch<AppDispatch>() // Export a hook that can be reused to resolve types

export default store

CodePudding user response:

You are doing const middleware: Middleware[] = ... which explicitly eliminates the specific types stored in the array and only retains that they are Middleware, instead do const middleware = [...] as const to retain as much information about the contents as possible. (and then use type assertions to allow the list to be modified without retaining those types since you can't possibly rely on then anyway)

  • Related