Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why Is React Context.Provider Necessary (Or useful)?

The reason React has contexts is to allow for multiple sibling components to share a piece of state-data. It is the go-to method for allowing two unrelated components to read/write in shared variables. The reason it is necessary is that React has no way to easily source a data value to multiple screens without actually passing that data between screens. Instead, it allows each screen access to the data when it needs it.

So... The implementation requires that a component be created, called a Context.Provider component, and then you have to wrap the components who need access to the shared data inside the Context.Provider. But why? Why on earth is that a requirement? Contexts are designed sharing data between components who aren't hierarchally related, and were required to put the components within a heirarchy to do so?

It would be 100 times more straight forward and just as effective to simply drop the requirement of using a Context.Provider, simple have the useContext function give access to a set variable by default:

// In ctx.js
import React from 'react';
export default CTX = React.createContext({val: "value"});
// In compA.js
import CTX from './ctx.js';
import {useContext} from 'react';
function A(props) {
    var [context, setContext] = useContext(CTX);
    console.log(context); //Logs {val: 'value'};
    setContext({val: "newValue"});
}

Then later on, assuming component B renders after A:

import CTX from './ctx.js';
import {useContext} from 'react';
function B(props) {
    var [context, setContext] = useContext(CTX);
    console.log(context); //Logs {val: 'newValue'};
}

The above usage, if it actually worked, solves the task of "sharing data between unrelated components", and is much much simpler than requiring an entire new component be defined in the context file. This solution is better because: 1. No required restructuring of the application. You don't need to wrap components in a provider. 2. Any Components can just ask for any shared state easily, and they can set the shared state easily. 3. Easier to understand with much less code involved (One line of code for import and one line to initiate the context). 4. Doesn't sacrifice anything. This method allows for easy sharing of state between components, which is the entire reason of contexts in the first place.

Am I crazy? Is there a legitamate reason that we'd absolutely need to wrap our components up in a special component to share data?.. Why can't the shared state just exist independently? Its like they chose a bad solution... Why make every developer wrap there components in another component before using shared state, why not just let the developer use the damned shared state when they need to use it instead of jumping through a hoop? Someone please educate me.

Edit: One answer said that with my described method we wouldn't be able to access multiple contexts with a single component. That is false. It is actually easier with my described method:

// In context.js
export const CTX = React.createContext({val: "val"});
export const CTX2 = React.createContext({val2: "val2"});
// In app.js

function App(props) {
    const [state, setState] = useContext(CTX);
    const [state2, setState2] = userContext(CTX2);
    return (<></>);
}

Easy. No need for Context.Provider. This is multiple contexts being used in one component, requiring just two calls to useContext versus wrapping your entire application in two nested contexts, which is what is what you have to do with current Context.Provider method...

like image 595
ICW Avatar asked Nov 23 '19 21:11

ICW


People also ask

Why we use provider in React Redux?

Provider is a component given to us to use from the react-redux node package. We use Provider in order to pass the store as an attribute. By passing the store as an attribute in the Provider component, we are avoiding having to store the store as props.

When should I use React context?

Context is primarily used when some data needs to be accessible by many components at different nesting levels. Apply it sparingly because it makes component reuse more difficult. If you only want to avoid passing some props through many levels, component composition is often a simpler solution than context.

Can we use context without Provider?

All consumers that are descendants of a Provider will re-render whenever the Provider's value prop changes. In other words, If you don't wrap your components with Context. Provider they won't get re-rendered when the someValues in createContext(someValues) changes.

What is use context used for?

“useContext” hook is used to create common data that can be accessed throughout the component hierarchy without passing the props down manually to each level. Context defined will be available to all the child components without involving “props”.


1 Answers

Mate, answer is simple. React component only re-renders when it's props or state changes. Without Context.Provider component react will never understand when to re-render child components, thus you will have stale, render-blocked components.

like image 87
QurcoJr Avatar answered Oct 14 '22 14:10

QurcoJr