react-boilerplate
has a utility injectReducer
that is used to allow a reducer to be asynchronously attached to the store
, and in the reducers.js
file for the entire application, createReducer
spreads out these injectedReducers
into the state so that you have a state shape as follows:
{
route: routeReducer,
language: languageProviderReducer,
container1: container1Reducer,
container2: container2Reducer,
container3: container3Reducer,
}
I would like instead to spread out these container-specific reducers to a subkey of the global state like so:
{
route: routeReducer,
language: languageProviderReducer,
ui: {
container1: container1Reducer,
container2: container2Reducer,
container3: container3Reducer,
}
}
I naively tried to modify the reducers.js
method createReducer
like so:
export default function createReducer(injectedReducers) {
return combineReducers({
route: routeReducer,
language: languageProviderReducer,
ui: (injectedReducers) ? combineReducers(injectedReducers) : ((state = {}) => state),
});
}
or maybe:
export default function createReducer(injectedReducers) {
return combineReducers({
route: routeReducer,
language: languageProviderReducer,
ui: combineReducers(injectedReducers || {}),
});
}
But now when I try to load any container, I get an error: TypeError: Cannot read property '_currentElement' of null
.
What is the easiest path to achieve the kind of state shape I want using injected reducers and react-boilerplate
?
The key for me I believe was to only add the ui
key when it was needed (when at least one injectedReducers
was present).
/**
* Creates the main reducer with the dynamically injected ones
*/
export default function createReducer(injectedReducers) {
const reducersToCombine = {
form: formReducer,
language: languageProviderReducer,
route: routeReducer,
};
if (injectedReducers && Object.keys(injectedReducers).length > 0) {
reducersToCombine.ui = combineReducers(injectedReducers);
}
return combineReducers(reducersToCombine);
}