I'm trying to use redux with NextJS and class components but can't figure out how to get rid of this error:
Error: Could not find "store" in the context of "Connect(CounterDisplay)". Either wrap the root component in a <Provider>, or pass a custom React context provider to and the corresponding React context consumer to Connect(CounterDisplay) in connect options.
// pages/_app.js
import '../styles/globals.css';
import 'bootstrap/dist/css/bootstrap.css';
import {Provider} from 'react-redux';
import {useStore} from '../core/redux/store';
export default function App({Component, pageProps}) {
const store = useStore(pageProps.initialReduxState);
return (
<Provider store={store}>
<Component {...pageProps} />
</Provider>
);
}
// pages/index.js
import React from 'react';
import Page from '../components/page'
import CounterDisplay from '../components/CounterDisplay';
export default function Index() {
// return <Page />
return (
<React.Fragment>
<CounterDisplay/>
</React.Fragment>
)
}
// components/CounterDisplay.js
import React from 'react';
import connect from 'react-redux/lib/connect/connect';
class CounterDisplay extends React.Component {
constructor(props) {
super(props);
}
render() {
return (
<div>
<span>{this.props.count}</span>
</div>
);
}
}
function mapStateToProps(state, ownProps) {
return {
count: state.count
}
}
export default connect(mapStateToProps)(CounterDisplay);
Weird thing is that I already wrapped the root component in a <Provider> so it should work fine according to the error message.
EDIT:
// core/redux/store
import {useMemo} from 'react';
import {createStore, applyMiddleware} from 'redux';
import {composeWithDevTools} from 'redux-devtools-extension';
let store;
const initialState = {
lastUpdate: 0,
light: false,
count: 0,
};
const reducer = (state = initialState, action) => {
switch (action.type) {
case 'TICK':
return {
...state,
lastUpdate: action.lastUpdate,
light: !!action.light,
};
case 'INCREMENT':
return {
...state,
count: state.count + 1,
};
case 'DECREMENT':
return {
...state,
count: state.count - 1,
};
case 'RESET':
return {
...state,
count: initialState.count,
};
default:
return state;
}
};
function initStore(preloadedState = initialState) {
return createStore(
reducer,
preloadedState,
composeWithDevTools(applyMiddleware()),
);
}
export const initializeStore = (preloadedState) => {
let _store = store ?? initStore(preloadedState);
// After navigating to a page with an initial Redux state, merge that state
// with the current state in the store, and create a new store
if (preloadedState && store) {
_store = initStore({
...store.getState(),
...preloadedState,
});
// Reset the current store
store = undefined;
}
// For SSG and SSR always create a new store
if (typeof window === 'undefined') return _store;
// Create the store once in the client
if (!store) store = _store;
return _store;
};
export function useStore(initialState) {
const store = useMemo(() => initializeStore(initialState), [initialState]);
return store;
}
useStoremethod. Could you share yourredux/store.jscode and also theComponentcomponent's code that you call inApp?