I learn the Hooks锛宨t's so good!
Bug when I use hooks: useReducer銆侷 confused by multiple provider.
app.js
:
import Provider from './store/index.js';
ReactDOM.render(
<Provider>
<Router history={history}>
<Layout>
<Switch>
<Route ... />
</Switch>
</Layout>
</Router>
</Provider>,
CONTAINER
);
./store/index.js
import providerOne from './providerOne.js';
import ProviderTwo from './providerTwo.js';
import ProviderThree from './providerThree.js';
// there maybe have many providers...
return (
<ProviderOne>
<ProviderTwo>
<ProviderThree>
{props.children}
</ProviderThree>
</ProviderTwo>
</ProviderOne>
);
./store/providerOne.js
const Context = React.createContext();
const initState = [];
const reducer = (state, action) => {
switch (action.type) {
case 'xxx':
return xxx;
default:
return state;
}
};
const ProviderOne = (props) => {
const [state, dispatch] = React.useReducer(reducer, initState);
return <Context.Provider value={{ state, dispatch }}>{props.children}</Context.Provider>;
};
export default ProviderOne;
In file ./store/index.js
, I must write many times <Provider>
structure.
There is any way to solve it.
Hey @hangyangws , I was just thinking about the same problem, and I've found the solution for this in this repo: https://github.com/FormidableLabs/react-context-composer
This solution was fine for me, hope it helps you too.
Simply put, if you want to get rid of the deep nesting of context providers you can write a util functional component like this:
export const ContextProviderComposer = ({contextProviders, children}) => {
return contextProviders.reduceRight((children, parent, index) => React.cloneElement(parent, { children }), children);
};
ContextProviderComposer.propTypes = {
contextProviders: PropTypes.arrayOf(
PropTypes.element,
).isRequired,
children: PropTypes.node.isRequired,
};
And you can use it in a component by listing your context providers:
import providerOne from './providerOne.js';
import ProviderTwo from './providerTwo.js';
import ProviderThree from './providerThree.js';
return (
<ContextProviderComposer contextProviders={[
<ProviderOne key={0}/>
<ProviderTwo key={1}/>
<ProviderThree key={2}/>
]}>
{ props.children }
</ContextProviderComposer>
);
We use the issue tracker for bug reports and feature requests.
If you have a question, please check our community support resources:
https://facebook.github.io/react/community/support.html
I have created another state management library that is better at service composition. Here is a demo of avoiding provider hell. Feel free to try it or read its source(100 lines of code)!
Most helpful comment
Hey @hangyangws , I was just thinking about the same problem, and I've found the solution for this in this repo: https://github.com/FormidableLabs/react-context-composer
This solution was fine for me, hope it helps you too.
Simply put, if you want to get rid of the deep nesting of context providers you can write a util functional component like this:
And you can use it in a component by listing your context providers: