I have this userContext
file:
import React from 'react'
const userContext = React.createContext({ loggedInUser: {} })
export { userContext }
I provide correctly a value in App
:
import { userContext } from './../contexts/UserContext'
class App extends Component {
//...
componentDidMount = () => {
this.authServices
.isLoggedIn()
.then(response => this.setState({ loggedInUser: response.data })
.catch(() => this.setUser(undefined))
}
return (
<>
<userContext.Provider value={this.state.loggedInUser}>
<Navigation/>
</userContext.Provider>
</>
)
}
And can access that value in any nested component such as in Navigation
:
/* ... */
<userContext.Consumer>
{value => value && <h1>Hi! {value.username}</h1>}
</userContext.Consumer>
/* ... */
How can I change from these nested components such as Navigation
the value from the loggedInUser
property in the context?
I don't find the way to attach methods to the context and use them, for example, when user logs out in the Navigation
component:
/* ... */
logOut = () => {
this.authService
.logout()
.then(() => /* modify here the loggedInUser from the context */ )
/* ... */
Please note this is a stateful component and I need a non-Hooks solution.
First you need to create a function that changes the user data and pass it in a context so child components can leverage it.
updateUserData = (userInfo) => {
this.setState({ loggedInUser: userInfo })
}
After that you can pass that function in the context:
<userContext.Provider value={{
loggedInUser: this.state.loggedInUser,
updateUserData: this.updateUserData
}}>
<Navigation/>
</userContext.Provider>
Since you are accessing context Provider
the old way you will need to attach
the static contextType = userContext;
on top of your class to be able to access context value like this outside of your render method:
const { loggedInUser, updateUserData } = this.context;
Now in your logOut
access the updateUserData
like above and pass it the new userData
.
Here is more info about contextType
:
https://reactjs.org/docs/context.html#classcontexttype