Around a decade ago, Facebook started looking for a way to modernize its web app. It was becoming increasingly complicated, and they needed a framework to make it easier to build and maintain. To fix this, they created a project called Bolt. Bolt was an MVC framework built on top of JavelinJS, and it solved many of the problems Facebook had. However, it was not perfect. Jordan Walke, a developer at Facebook, created the next iteration of Bolt, called FaxJS. It offered many features that React has today, like rendering on both client and server, DOM diffing, and more. Jordan Walke renamed FaxJS FBolt and started using it in Facebook's codebase.
React started growing quite a bit after that. React's GitHub repository reached 10k stars in late 2014, 20k in 2015, and 50k in 2016. Additionally, React's ecosystem started to grow with things like Reactiflux.
Hooks are ways of defining lifecycle methods in functional components. In 2019, React released hooks, which completely changed the way people wrote applications in React. Before hooks existed, you had to use classes for stateful components. Functional components could only be simple components that just relied on props. However, hooks offered a way of accessing state through functions, which opened the door to completely using functional components. Nowadays, most new applications use hooks instead of class components, as hooks are simpler to use and more concise.
React automatically updates your UI if your data changes, saving a significant amount of time. For example, if you had a table of various transactions set to update every 15 seconds, you would have to define the difference checking and updating manually. However, with a framework like React, you can just change the value of the data, and everything happens for you. Dynamic updating also makes your UI easier to reason with, as you can guarantee it represents the data.
React can render UI on both the client and server with the same code. That opens up opportunities for server-side rendering and hydrating on the client. In this way, React contrasts with lots of traditional templating languages where you could generate static HTML but not make that automatically interactive.
React does this through two different APIs. Their primary rendering API function exposed through
render, which renders the JSX passed on to the client. However, to render HTML on the server, there is
react-dom/server, which renders static HTML that can be hydrated later using
Remix is a new React framework (like Next.js), created by the people who made React Router, that was only recently open-sourced but has been growing very quickly. Remix promises better integration with web platform features, integration with the edge, and simpler isomorphic code. Remix has already managed to gain 12k stars. Another unique thing about Remix is that instead of offering static site generation and dynamic server-side rendering, it focuses entirely on server-side rendering. That means that while Remix does not support static site generation, if you prefer rendering dynamic data on the server rather than using API fetching on the client, Remix works quite well. Of course, there are tradeoffs to both rendering on the server and fetching data on the client for dynamic data, and it depends on your use case. Finally, due to the author's experience building React Router, Remix has advanced routing, with features like nested routing and isolated errors.
React 18 is an upcoming React release that offers many new features, like the concurrent renderer. The concurrent renderer allows for multiple versions of the UI to be built at once, which opens up opportunities for new features like automatic batched updates, streaming server-side rendering, and more. These features help improve performance. For example, automatic batched updates reduce the amount of UI updates needed, which increases performance on the client.
There are numerous approaches to using CSS in React. Of course, you can use native CSS, but there are many other approaches that work better with React's UI style.
Atomic CSS works well with React due to its scoping. Since the styles are atomic, they are automatically scoped to just the elements that use them, making it easier to reason about styling with components. Additionally, Atomic CSS's repetition can be solved using components. Some of the most notable Atomic CSS libraries currently are Tailwind and UnoCSS. Tailwind is, by far, the most dominant Atomic CSS library out there due to its wide variety of features and ease of use. UnoCSS is a more recent project that is significantly faster and more flexible than Tailwind.
While React has many advantages, performance is not one of them. Luckily, there are replacements for React that retain a identical or almost identical API. The most notable are Preact and Solid. First, we have Preact. Preact is faster and significantly smaller (3kb Gzipped) than React while having an identical API. You can use Preact almost anywhere, and it can be used as a drop in replace with
preact/compat. Second, there is Solid. Solid does not have an identical API to React, but the ways it differs allows it to get a large performance advantage. In terms of runtime performance, Solid is significantly faster than both Preact and React. Solid achieves this by forgoing a virtual DOM and building components only once instead of whenever state updates. Solid is also smaller than React, although it is a bit bigger than Preact.
I hope you learned something from this today. If you enjoyed reading this, sign up for the mailing list here and subscribe to RSS to get more of these articles. Thanks for reading!