🚀Debugging Microservices & Distributed Systems
5 min read

Speeding Up React Apps with Code Splitting and Lazy Loading

Performance is not a luxury; it's a necessity

Code splitting and lazy loading are two crucial techniques for modern developers looking to enhance their web applications’ efficiency and user experience.

This is especially true given that search engines like Google now use Core Web Vitals as a ranking factor, rewarding faster websites with better search engine rankings.

Let’s dive into how these techniques can be implemented in a React application.

Understanding Code Splitting and Lazy Loading

Code Splitting is a technique where you divide your code into various bundles or chunks, which are then loaded on demand.

It’s particularly useful in large-scale applications, as it helps reduce the initial load time by loading only the necessary code for the current view

Instead of loading the entire application bundle upfront, code splitting allows you to load only the necessary parts for the current page or feature, reducing the initial load time.

Lazy Loading, on the other hand, is a strategy to delay the loading of non-critical resources at page load time. In React, this translates to rendering components only when they are actually required, thus reducing the amount of code processed and rendered on initial load.

Implementing Code Splitting and Lazy Loading in React

React offers a built-in way to implement lazy loading through the React.lazy function. It works seamlessly with dynamic import(), allowing you to load components only when they are required.

Consider a React application structured with various pages such as SignIn, SignUp, BlogList, etc.

Implementing lazy loading for these components using React.lazy

First, we import the necessary hooks from React:

import { Suspense, lazy } from "react";

Then, we define our components with the lazy function:

const SignIn = lazy(() => import("./pages/auth/SignIn"));
const SignUp = lazy(() => import("./pages/auth/Signup"));

Using Suspense to Wrap Lazy Components

Suspense is a React component that lets you specify the loading indicator in case the component takes time to load. In our App component, we wrap our routes with Suspense:

function App() {
return (
<Suspense fallback={<div>Loading...</div>}>
{/* ... rest of the component */}
</Suspense>
);
}

Routes with Lazy Loaded Components

Inside the Routes and Route components, we use the lazy-loaded components.

<Routes>
<Route path="/sign-in" element={<SignIn />} />
<Route path="/sign-up" element={<SignUp />} />
{/* ... other routes */}
</Routes>

Lazy Loading CSS for Better Performance

CSS optimization is as vital as JavaScript code splitting and component lazy loading, though it often receives less attention. The impact of large CSS files on load time and rendering performance cannot be overstated.

Strategies for Lazy Loading CSS

  1. Splitting CSS: Similar to JS, split your CSS into chunks corresponding to different components or routes.
  2. Conditional Loading: Load CSS files only when the associated component or route is active.
  3. Dynamic Import of CSS
useEffect(() => {
import("react-toastify/dist/ReactToastify.css").catch((error) =>
console.error("Failed to load react-toastify CSS", error),
)
import("react-quill/dist/quill.snow.css").catch((error) =>
console.error("Failed to load Quill CSS", error),
)
import("react-tagsinput/react-tagsinput.css").catch((error) =>
console.error("Failed to load react-tagsinput CSS", error),
)
import("material-icons/iconfont/material-icons.css").catch((error) =>
console.error("Failed to load material-icons CSS", error),
)
}, [])

Libraries like styled-components or emotion allow you to include styles directly within your component files. This way, styles are loaded and applied only when the component is rendered.

Benefits of CSS Optimization

  1. Reduced Initial Load Time: Minimizes the amount of CSS loaded initially.
  2. Improved Render Performance: Prevents render-blocking by loading only necessary styles.
  3. Enhanced User Experience: Faster load times and smoother transitions between components.
  4. Performance and SEO benefits

Implementing these techniques above offers numerous benefits:

  1. Improved Load Time: Reduces the initial load time, making your application more responsive.
  2. Efficient Resource Utilization: Smaller initial loads translate to lower bandwidth consumption.
  3. Better User Experience: Users enjoy a faster and smoother browsing experience.
  4. Enhanced SEO: Search engines, including Google, favor websites with better performance metrics.
  5. Faster load times contribute positively to Core Web Vitals, a key metric used by Google for ranking websites.

Core Web Vitals and SEO

Google’s Core Web Vitals are a set of specific factors that Google considers important in a webpage’s overall user experience

Each of the Core Web Vitals represents a distinct facet of the user experience, is measurable in the field, and reflects the real-world experience of a critical user-centric outcome.

The metrics that make up Core Web Vitals will evolve over time. The current set for 2020 focuses on three aspects of the user experience—loading, interactivity, and visual stability—and includes the following metrics (and their respective thresholds):

Largest Contentful Paint (LCP): measures loading performance. To provide a good user experience, LCP should occur within 2.5 seconds of when the page first starts loading.

img

Interaction to Next Paint (INP): measures interactivity. To provide a good user experience, pages should have a INP of 200 milliseconds or less.

img

Cumulative Layout Shift (CLS): measures visual stability. To provide a good user experience, pages should maintain a CLS of 0.1. or less.

img

It’s a good idea to keep an eye on your Core Web Vitals regularly to spot and fix any performance issues on your website or app.

Optimizing your React application with code splitting and lazy loading is more than just a performance enhancement. It’s a crucial aspect of delivering a superior user experience and improving your website’s visibility on search engines.

By loading only what’s necessary, when it’s necessary, you cater to both your users’ needs and the requirements of search engines.


Related Articles

If you enjoyed this article, you might find these related pieces interesting as well.

Recommended Engineering Resources

Here are engineering resources I've personally vetted and use. They focus on skills you'll actually need to build and scale real projects - the kind of experience that gets you hired or promoted.

Imagine where you would be in two years if you actually took the time to learn every day. A little effort consistently adds up, shaping your skills, opening doors, and building the career you envision. Start now, and future you will thank you.


This article was originally published on https://www.trevorlasn.com/blog/react-lazy-loading. It was written by a human and polished using grammar tools for clarity.

Interested in a partnership? Shoot me an email at hi [at] trevorlasn.com with all relevant information.