React Provider Hell
React Provider Hell
#Issue
const context1 = createContext({});
const context2 = createContext({});
const context3 = createContext({});
const context4 = createContext({});
const ChildApp = () => {
const v1 = useContext(context1);
const v2 = useContext(context2);
const v3 = useContext(context3);
const v4 = useContext(context4);
return (
<>
<h2>ChildApp</h2>
{v1.v}
{v2.v}
{v3.v}
{v4.v}
</>
);
};
const App = () => {
return (
<>
<context1.Provider value={{ v: 1 }}>
<context2.Provider value={{ v: 2 }}>
<context3.Provider value={{ v: 3 }}>
<context4.Provider value={{ v: 4 }}>
<ChildApp />
</context4.Provider>
</context3.Provider>
</context2.Provider>
</context1.Provider>
</>
);
};
render(<App />);
jsx
#Solution
const context1 = createContext({});
const context2 = createContext({});
const context3 = createContext({});
const context4 = createContext({});
const ChildApp = () => {
const v1 = useContext(context1);
const v2 = useContext(context2);
const v3 = useContext(context3);
const v4 = useContext(context4);
return (
<>
<h2>ChildApp</h2>
{v1.v}
{v2.v}
{v3.v}
{v4.v}
</>
);
};
const buildProvidersTree = (componentWithProps = []) => {
return ({ children }) => {
return componentWithProps.reduceRight((acc, [Provider, props]) => {
return <Provider {...props}>{acc}</Provider>;
}, children);
};
};
const ProvidersTree = buildProvidersTree([
[context1.Provider, { value: { v: 1 } }],
[context2.Provider, { value: { v: 2 } }],
[context3.Provider, { value: { v: 3 } }],
[context4.Provider, { value: { v: 4 } }],
]);
const App = () => {
return (
<>
<ProvidersTree>
<ChildApp />
</ProvidersTree>
</>
);
};
render(<App />);
jsx