Getting to React 19 has been quite the journey, but it's finally here...
Thank you bolt.new for spo...
Video Transcript:
the journey to react 19 has been wild to put it lightly there has been so much work going into this release everything from the new server component patterns to all the crazy stuff with used transition to the ways they kind of broke suspense but not really it's been a journey but we're at the end of it and react 19 is finally stable and ready to use today not that you couldn't use it before I'm sure a lot of us were on nextjs and taking advantage of the canary with app router and ser you get the point is actually officially stable now and there are some changes that are really important to understand so if you use react make sure you stick around but first a quick word from today's sponsor today's sponsor is bold. new and I actually already shot this ad and I threw it away because I just learned something that I think is more important than all of the other stuff I've recorded if you don't already know b. new is the quick way to spin up an app using Ai and actually prompt and have a whole editor in the browser it's by the people over at stack they know how to make a good editor in the browser and it is one of the best ways to start your new app today what I didn't realize is the entire thing is open source what why did no one tell me this whole thing prompts and all they're not hiding it so if you don't want to pay you can go self-host it and do whatever you want I've even seen people forking it and throwing it on Docker but I just think it's really really cool that you can go in and actually understand how it's generating your code that makes it so much more trustworthy than all of the similar Tools in my opinion like I'm a cursor guy it's closed Source I don't know how it's generating stuff here you go see every single little bit and it's not like it just starts apps in one specific way that they like you can tell it to start an astro app a remix app a spelt app think you even tell it to do a python app it knows what it's doing it can even make presentations with slev and when you want to deploy you just tell it to deploy and it does it automatically for you on netlify I've been really happy with both it's been a super fun way to start building your apps and you should give it a shot if you haven't check them out today at soy.
l/ bolt or you can just go to bolt. new react 19 is now t for what it's worth most of this post is the same as the release candidate post back in April I have a whole video about that if you haven't seen it kind of crazy to think it's been since April that the release candidate came out but uh we're through it it's here let's focus on the important New pieces which are improvements to suspense and the reactdom static apis both of which are really cool the suspense changes are what held up the react 19 release to quickly TDR suspense is a way to have a good fallback State when components are doing things that are asynchronous be it fetching data generating things that are require an async call just things that you don't want to block your main thread for previously the way suspense worked is it would try to render all of the components go through all of the children one at a time once it was done it would check to see if any of them were waiting for things and if they were it would throw into the fallback state which is in this case just a loading div the problem was it had to go through all of the sub components and start their renders before you could get to the load State react 19 originally introduced a change where it would go through these components one at a time until it found one that needed data or something that it was blocking on and it would immediately go back up and throw the fall back and then go through the rest of the components one at a time the problem is that means all of these aren't being kicked off at the same time back in react 18 this would have taken 3 seconds to render roughly because all three of these components would have started at the same time so this timer this timer and this timer are all going together in parallel because of how Facebook uses react they fetch all of their data at once when the page loads so having to wait for all of the components was causing the fallback Behavior to be slower so they decided to just stop once the first component is hit and not start the next ones but if you're using react and suspense in a way where you actually want to kick off all of these things at once the performance was really bad most people aren't using suspense at all to be fair but the ones who were were not using it too too often in that way I know if you're heavy on things like use suspense query and react query or deep in the react 3 fiber world you might be using it for really cool stuff and if you are doing those things this was a really really bad change there was a bunch of outrage I have a long video detailing all of that but we finally have a resolution now in react 19 when a component suspends react will immediately commit the fallback of the nearest suspense boundary without waiting for the entire sibling tree to render that's the change I was talking about before but they added to it after the fallback commits react schedules another render for the suspended siblings to pre-warm Lazy requests in the rest of the tree what this means is after it realizes here oh this is suspending throw the fall back then go through and kick off the rest of the children for their renders that allows you to get basically the exact same performance while also getting the fallback State much earlier which is an awesome change for us suspense NS this primarily benefits big code bases with giant components especially those that are heavily using suspense most of you don't have to worry about this but it's awesome that they found a compromise here that allows for a code base like Facebooks to be as performant as possible while also allowing for us to use it for crazy things like we see in react 3 fiber and as they show here you had to wait for all of the children before you could see the loading State now as soon as one child suspends you see the loading State and the rest start to get rendered this change means that the suspense fallback displays faster while still warming lazy requests in the suspended tree this change took a while for them to get right to get tested everywhere they wanted it to and this is the change that blocked react 19 it's here it works they released a ga of this a few weeks ago everyone seems happy I haven't seen anyone complain just yet so I think I hope this is the end of the suspense drama what a susp ense F event it has been just to show this is a very good change Dominic who is the lead maintainer for react query and tan stack query did a quick demo using the new version of suspense in react 19 said it's not quite the same as it was in V8 but it is definitely the perfect trade-off he was very happy with the results so he said start fetch one then start fetch two render fallback both fetches used to start at the same time react 19 would render the fallback after fetch one wait and then start fetch two now it starts fetch one renders the fallback and then right after kicks off fetch two you get the fall back faster and you have to wait for the Finish awesome A++ we're going to cover the other big change quick and then we're going to do a higher level why you should care about react 19 the other big change here is that react Dom static has a couple new helpers for static site generators pre-render and pre-render to node stream these new apis improve on render to string by waiting for data to load for static HTML generation they're designed to work with streaming environments like nodes streams and web streams for example in a web stream environment you can pre-render a react tree to static HTML Now using pre-render so here we see we call the pre-render function from react Dom static we pass it our app jsx component our app we give it any bootstrap scripts that it requires for things that it does we get our Prelude which is the response that we want to send to the user and then we can return that as HTML prender apis will wait for all data to load before returning the static HTML stream streams can be converted to Strings or sent with a streaming response they do not support streaming content as it loads which is supported by the existing react Dom server rendering apis this is really cool because it allows you to do like a static HTML pre-render or even like generate something like a Blog that doesn't need react code at all in it in the client side at least but you're still able to use react on the server kind of gives you all of the benefits that you're looking for really nice win and I've seen some really crazy stuff going on with this so previously if you wanted to use react on the server like this you had to use their pre-render function from the react Dom server package which presumes that it can resume the results on the client side which is which isn't always the case and you'll see it still has the Prelude and postponed concept where the Prelude is the first thing it responds with the postponed is what comes after nice that these things are accessible in places that aren't just the crazy server component world like everyone should be able to pre-render their stuff and there's a lot of places this would be very beneficial and since it's a static thing you can now run this in something like your build instead of having to use this for a server rendered thing very nice these pieces are going to make it a lot easier for people to make their own I don't to encourage this but you can kind of more easily make your own bespoke framework light around what these Primitives offer and I'm really excited to see more bespoke react Frameworks popping up taking advantage of these things we have Sebastian lber here who is planning on using this for SSG and docurus I also saw that you now have an RS pack option for docusaurus that's really cool to see great work on all that docusaurus is one of the best options for documentation yeah there's no render to string equivalent in react 18 very good context to have render to string was always a bit slow but it's good to see that we can get around all of these things I certainly talked about this in the previous video but it's so nice that we finally can get way better diffs when we have hydration errors hydration errors are the worst I totally understand why people want to leave react when they run into them for the first time now we get way better errors where it says why it thinks the thing happened why the branch between server and client may have occurred in the specific diff that it sees in the HTML really really nice for the weird cases where your server and your client render things slightly differently hopefully by now you have a rough idea of what react 19 specifically is adding but I want to talk more about the mindset shift that react 19 represents back in the day when we built something with react it would look something like this where we had our HTML had ahead it would load some script it would have a different metadata in it like your title stuff like that on the head and then your body would have an ID rout or even more commonly app and one of these scripts would be script Source equals app bundle. js so when you actually went to this website it would have to fetch all of the things you have up here all the CSS all the script tags and show you whatever the default state is in your body until the JS loads and then can come in and take over from here react didn't start until the page had loaded the JS had loaded been parsed and run and then you were actually using react nextjs had the goal of taking over this part and giving it a bit more of a relationship with the react code let's say you have a specific route that needs a different title like on Twitch when you go to my channel it should have different data in the head tag so when you send that link to somebody it can correctly embed the metadata in the Discord message the Tweet whatever else using the right info for that specific page previously this concern largely existed outside of reacts area and that's why something like next was so important because it allowed you to control those things on a per route basis while using that alongside react that was nice but it was really like a a one-way relationship where it was like nextjs wrapped the HTML which wrapped the react so if we were to diagram this it's kind of like we had HTML and then a smaller Circle in here which was react but the HTML was just the container that the react was in react had no control of it but we needed more control of the HTML so new tools like nextjs were made in order to give us that extra control also to fix the wos that were our bundle and everything else alongside that over time we've realized that this isn't ideal because it's very One Way nextjs can do things outside of reacts bubble but all it can really do is create the pages in the environment it can't really interrup with the react part on the inside the perfect example of how this worked is something like get server side props where you would have a function in a specific route on your code base that would generate data and it would pass that to the top of the react app that you would have to pass down component by component but the idea of something within react having access to something from next wasn't real the only way a given component could get something from next is if you passed it to the root and then it went through all the way down to that component if you you open up any page router app using next you'll see there's a little next data tag that gets embedded in the HTML that has all of those page props so that if a component tries to access them it has access there to then pass it through the react app but literally what is happening here is nextjs puts a script tag in HTML and then the react code is told to fetch that data from that point in the HTML there is no relationship between these they can't pass things back and forth it's literally just the from next being embedded in the HTML so that react can access it kind of like passes down back to react but there is no way for the react code to go back up and request different things request an update and really do much of anything it's just that next sends things to the HTML that then react has access to the new model is fundamentally different here in a way that's really exciting and honestly I can't really think of how to diagram it because it's kind of like react is just at all of the levels now so if I was to do this the like complex literal way it would be kind of like I put another circle out here that is also react but I don't think this is a fair way to think about it this is what it seems like when you first discover all these new tools and technologies that react is now this greater thing on the outside that is that controls your server and changes how everything works but I think of it a bit differently I think of server components in this whole new way of building almost like a bridge between the parts so we have this path that's been made between the server side the HTML that the user gets and the react side examples of how this works are things like the power of static rendering a component for your shell the unique capabilities we get with streaming where you can send down whatever is done immediately and then stream the rest in later which fits like the HTML layer and then all of the Power around the like passing something that only runs on the server down to the client my favorite demo and I have it in this project actually so here we have your classic tab component we've all seen these in docs where we have tab a b and c you can click to swap between the three if we look at the code things are going to be a bit interesting we have the page component which doesn't have used client which means this is a server component by default now when we look here we have my tab wrapper component that I imported and I'm passing it tab contents tab is a tab is B and tab a c so you would expect all of these to be logged there because I'm passing these components down so when the react code renders on the client that means it has to console log those right kind of they made a nice change where the logs on the server now get passed to the client so you can see them but in production you wouldn't get these logs because in production this code doesn't run on the client and it doesn't run on the client here either these logs are coming from the server because all three of those components get rendered on the server and then their results are passed down so that react can swap between them on the client side you can pass a server component's rendered output as a prop to a client component and then use client side state to swap between those different server rendered States this type of thing is what makes the new react model so special it's not just adding a couple features here and there to patch these broken parts it's rethinking how react interfaces with all of these other things the way I kind of think of this and it's going to make very little sense and I'm going to apologize in advance the first thing I would change is I'd put client in the middle here not react although obviously the client JS is running react but what react now thinks about is what subset of all of this can it provide the happiest path to so that the other half is way less complex I've almost felt all of these circles shrink as a result of how these new patterns work where a lot of things I would have to do to like generate a static shell for the different pages I had render something on the server and only pass down Parts I want to the client all of these things required so many hacks and so much weird F just just weirdness with your JS that's all gone with that the model is now very different and we have to think differently about how we write our react there were so many patterns and paradigms and ways of building that we had to do these ways because of the complexity around react like I know at twitch we had a go service that would generate the different HTML shells for different routes that would all just load the same react code in the end you might look at this and think it doesn't benefit you and something like server components doesn't matter cuz you're rendering everything on client hear me out for just one second let's say your page wasn't just this tab wrapper let's pretend it has a lot more stuff that it needs wouldn't it be nice if you didn't have to wait for all that JS to come in to then tell the browser everything else it needs like let's say this component has a specific font it needs or some CSS it has to load if we use server components literally just as a top level static wrapper and send everything else down on the client when it's ready you can basically move any existing react app to this pattern have a slightly better static shell that allows you to stream quicker and start fetching things like the fonts a little bit earlier previously you'd have to wait for the whole HTML to load then it would kick off the JS load if it had the CSS embedded in there awesome it can start if not it has to wait for react to then figure out what CSS it needs you end up waiting for the HTML then for react to load and run and identify what it needs off and it has to load additional bundles then you have to wait for it to add the right tags into the page to fetch things like your CSS like your fonts like all this other stuff while at the same time the content is starting to render with this model react can hoist all of those depths up so that they're in the HTML tag as soon as the page loads and then everything else comes in when it's ready this doesn't mean you have to run react on the server this is one of the most common misconceptions with server components is the idea that it has to run on a server when ever you go to the page there's a very real future coming where you can static render the server components where instead of thinking of a server component is a thing that runs on the server you could think of it as a different place that react was rendered in technically your Dev machine is a server so when you run npm run build on your machine you are running those server components on your device as a server and now you have those static pieces that come in on the client side when it's ready that is a really powerful thing the idea of server components not just as the thing that you use with nextjs when you run react on the server but as react being the piece that generates the HTML layer it's taken react's area of concern it expanded it slightly but it allows us to do the right thing for the user much more easily and to not have to patch that in with a ton of other tools I've seen some chaotic stuff of people brute forcing pre-rendering into react by doing things like spinning up the server hitting it via Puppeteer or playright saving the HTML response and then using that as the static site even Frameworks Like Remix used to recommend this strategy as the way of building your static parts of your react site the reality is that every website has some things that are static and some things that are Dynamic react used to only care about the dynamic parts and making those as easy to work with as possible and the reason for that was just that the dynamic parts were hard to do at the time when react happened static had been figured out we were deep in PHP and we were more than happy but jQuery was the wrong way to do the dynamic Parts it was better than what we had but it wasn't good enough Rea made Dynamic great it made it so great that static started to fall behind and the thing that's changed here the real mental model shift is that react isn't just concerned about the dynamic part anymore it's concerned about the holistic set of pieces that have to come together to make the experience great they're not prescribing every solution to every one of those parts but they're giving us what we need to assemble it how we want that's why things like the static apis are so useful because this shows that they're building ways for us to take advantage of this mindset in these new benefits of react without having to adopt something like nextjs yeah as Sebastian said Here remix and react router 7 do have pre-rendering and in the implementation it's surprising but they spawn a server and send real requests to it to generate the HTML that is how we've had to do this for a while but the ADV of these new apis is you could do this without all those weird hacks and the amount of those hacks that have made it into production the majority of like Fortune 500 react sites are probably doing something like that there's even a famous story of Netflix removing react what they actually did is they rendered the react app for their signin page on the server filled in a little bit of JS to make the form active and now they're sending almost no.