In my react app I have guest routes and protected routes. The protected routes are only accessible when the user is authenticated. Next to that, the main app routes are only accessible when the user has signed a contract and finished the onboarding. I'm keeping track of these steps with some extra properties assigned to the user.
My current flow is the following
The user enters the app and the function
fetchCurrentUser
is triggered inside the AuthContext Provider. If the call to the database returns data the propertyisAuthenticated
is set to true and the user data is set to thecurrentUser
state. If the calls returns an (unauthorized) errorisAuthenticated
is set to false. InitiallyisAuthenticated
is set tonull
so I can render a loader as long asisAuthenticated
is null.Let's assume the user wasn't logged in. Since
isAuthenticated
was firstnull
and nowfalse
the code isn't returning the<h1>Loading</h1>
loader anymore but will return a route. Because/
can't be accessed becauseisAuthenticated
is false, the app will redirect the user to the/login
pageWhen the user fills in the credentials and submits the data a cookie is returned from the backend and set in the browser. Now I want to re-trigger the
fetchCurrentUser
function to collect the user information. * To do this I setisAuthenticated
back to null and I navigate the user to the dashboard page/
. SinceisAuthenticated
isnull
the spinner will show up instead but the route is already/
.In the meantime
fetchCurrentUser
will do the api call with the cookie which will return the user data and setisAuthenticated
to true.
Short note for step 3 and 4. I think there are better ways to handle this so please don't hesitate to share a better solution.
Maybe there is a way to call the fetchCurrentUser
from the Login component and wait till the data is set and navigate the user afterwards? Because fetchCurrentUser
is more than an api call and the submit function has to wait till the whole function is done I should work with a promise but inside a promise I can't use async/wait to wait for the api call.
- Now that
isAuthenticated
is true and the user data is known and stored in the AuthProvider the routes can be rendered again. Since/
is a protected route the code will check ifisAuthenticated
is true and check to which route the user needs to be navigated. This part goes wrongWarning: Maximum update depth exceeded
but I don't know what I'm missing.
Code to test things out with some fake calls the represent the flow via
CodePudding user response:
It shows "Warning: Maximum update depth exceeded" because when you call getCurrentUser() method if isAuthenticated not false the method triggered 2 states and React sees that there are two states and React updated two states in the same time (automatic batching) and when isAuthenticated get new value useEffect() works again it sees that isAuthenticated true ant it is again changes states it happens again again and to infinity for that it show that error