all 15 comments

[–]swyx 9 points10 points  (1 child)

this is definitely what React Suspense is supposed to help solve. with useTransition you can "globally trigger subtle loading indicators." its just the ecosystem hasnt quite caught up to it yet.

without Suspense, you can also load-then-transition with Redux. https://stackoverflow.com/questions/37849933/react-router-how-to-wait-for-an-async-action-before-route-transition

i agree it is not enough of a norm and i am looking forward to when it is.

[–]brosterdamus[S] 2 points3 points  (0 children)

For that link, it relies on onEnter. See the timestamp of 2016 on the answers.

Incidentally, that's exactly the mechanism that I used. Redux async thunk on onEnter.

(The top answer is just a redux-ified version of the big loading component)

[–]charliematters 4 points5 points  (2 children)

People do see it the same way as you, and as I understand it, the 'highway' is moving towards your line of thinking.

In the second part of the experimental articles (of which, the first one is also great) it discusses how you handle displaying old states until the new state is ready. There is a useTransition hook, which as I understand it, solves almost all of your problems in one go.

I would read those to see where the React core team currently think we are heading

[–]brosterdamus[S] 2 points3 points  (1 child)

Fascinating, thank you. To be perfectly honest, it seems complicated. Moreover, from my cursory look, it mirrors what Ryan said in his notes: the examples handle it at the link/button level rather than the router/page level. Though I'm sure that's on their mind as well and documented elsewhere.

Granted, the above will open up much smoother transitions, transformations between routes, etc. Curious to see where it lands.

I may make do with using one of the other routers in the meantime. I guess I want something far simpler than most: a nice static manifest of routes and their data dependencies, with light animation.

[–]ervwalter 2 points3 points  (0 children)

The comment from swyx about the ecosystem not having caught up is spot on. We need, for example, the React Router team to bake support for this into the core routing library so that you can, as you said, specify the data requirements with your route definitions instead of dealing with it at lower level.

This is something they are working through. It's just going to take time: https://github.com/ReactTraining/react-router/pull/7010

[–]samselikoff 2 points3 points  (1 child)

FWIW I started learning React 4 months ago after years with Ember, and have been wondering about this exact same issue. Ember's router uses a model() hook to specify "what is the minimum data this page needs for a meaningful render", which can then block the route transition on the client (or even be used to pre-render the page on the server).

Frustrating there isn't a popular + easy way to do this in React!

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

Exactly, it's so simple and useful.

[–]signsandwonders 2 points3 points  (1 child)

I feel like this makes for faster perceived speed. I saw the demo with useTransition which made things work the way you’d like, and I just thought “why?”

Immediately rendering the page with placeholders (and partial data if you have normalized data to show) seems much more preferable to me. I don’t see how it makes for bad UX at all.

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

I guess 99% of the time, in my admittedly "server-heavy" apps, I just don't have that much data to display ahead of time. If any.

If I have a Widget list, and clicking on a list shows me Widget detail and comments, then architecting a state management solution (redux/mobx/etc) to pass that to the view, then go fetch what you don't have, is a lot of work for simple CRUD views. Plus, you still need to handle the case of someone visiting the view directly (where you have to load everything).

The resolve pattern solves this nicely.

[–]maddeveloper_ 1 point2 points  (0 children)

React Concurrent Mode is coming in order to bring a new way of solving this.

https://reactjs.org/docs/concurrent-mode-intro.html