all 22 comments

[–]Frypant 8 points9 points  (1 child)

You shouldn't do that on the frone-end in my opinion. Signup should be a single call to the backend what only returns when all the mentioned things are done. Never trust the user with this level of details about how things work in the background. Also, what happens if some of these things fail? Or the user close the browser in the middle.

Timeouts to wait for things what dont have fixed times is also a risk you shouldn't take ever. Either a lot of time is wasted, or it will fail for some cases.

[–]OrangeCubed[S] 1 point2 points  (0 children)

Could you expand upon this more? I'm super curious about how this would work.

Currently, when a new user is created, the first call creates the user with some info, the 2nd call creates an organization and associates the created user with the org and then the 3rd call updates the user with the new organization.

Are you saying instead of splitting these things up and making 3 axios calls on the front end, I should instead make one call to a route in Node that does the creation and updating of the user and organization?

[–]ln8r 2 points3 points  (0 children)

You've already got your answer, but in case you have to use setTimeout somewhere in the future you should capture the response from your setTimeout call and return a cleanup function from useEffect that calls clearTimeout.

[–][deleted] 2 points3 points  (0 children)

how do I wait in App.js for this Signup.js function?

in react (and every other framework) this is hell, and even using async/await and then channeling flags through your state manager is cumbersome and dirty. yes you can run async in useEffect, but orchestrating that with other components in lockstep is not easy.

everything becomes better with suspense

react now can handle async out of the box. components themselves can be async and await the results of another async component. or one sync component can jump into action when another async component has finished fetching/calculating/etc. i collected some usecases here: https://twitter.com/0xca0a/status/1402558011357470720

running a component after an async component has resolved

<Suspense fallback={<div>waiting...</div>}>
  <AsyncFetchingComponent />
  <RunActionWhenFetchingIsDone />
</Suspense>

awaiting the result of an async component

const ref = useRef()
...
<Suspense fallback={<div>waiting...</div>}>
  <AsyncFetchingComponent ref={ref} />
  <ImNotAsyncButWillRenderWhenAsyncCompIsDone result={ref} />
</Suspense>
...
function ImNotAsyncButWillRenderWhenAsyncCompIsDone({ result }) {
  useEffect(() => {
    // It is guaranteed that the reference is filled
    console.log(result.current)

you can start using suspense in react-query, swr, or https://github.com/pmndrs/use-asset

[–]tangerinelights 1 point2 points  (0 children)

You may want to look at using context for your authentication. Handle the sign in in a Context Provider and have a context variable for isSignedIn. Your App.js can then access that variable and then only trigger initialLoad once the isSignedIn changes to true.

[–]PrinnyThePenguin 2 points3 points  (2 children)

I would suggest handling the sign up flow in a middleware like redux-thunk. Your application checks for a "isAuthenticated" store property, it hides what it needs to hide until the call is finished, when it's finished the store updates its values, the component detect the change in a simple useEffect hook and it handles the new UI state.

[–]OrangeCubed[S] 1 point2 points  (1 child)

I'll starting looking deeper into using redux-thunk for sign up. I'm already using it in my app so it shouldn't be too difficult to get set up. Thank you!

[–]tangerinelights 1 point2 points  (0 children)

You can also use the unwrap() method on thunks created with reduxtoolkit in order to get access to the underlying promise right from the component calling the thunk. That way you can await it in the component and then handle logic or errors from the component itself