Code splitting

Elevate, May 20-22-2025, Miami Beach, Florida

As you continue to develop your application, the JavaScript bundle size will keep increasing over time, becoming one of the critical bottlenecks for performance and SEO. To solve this issue, Next.js allows developers to dynamic import components hence splitting the application bundle into smaller chunks and lazy load on demand.

In this article, you'll learn how to improve site performance with code splitting using dynamic imports.

Component based code splitting

The easiest way to do code splitting in commercetools Frontend is the per-component basis, where you lazy load components that aren't required on the initial page load. For example, the <Cart /> component is only needed for the cart page and can be lazy-loaded. You can lazy-load tastics while registering them in the frontend/frontastic/tastics/index.tsx as shown below

tastics/index.tsxtypescript
// ... imports for other tastics
import dynamic from 'next/dynamic';

const Cart = dynamic(() => import('./cart'), {
  loading: () => <h1>Loading cart...</h1>,
});

export const tastics = {
  'commercetools/ui/cart': Cart,
  // ... more tastics
};

The loading component appears as a fallback while the browser waits for the JavaScript bundle for the <Cart/>. In this example, the text Loading cart... appears while the request for the JavaScript bundle is pending.

But as soon as the JavaScript is loaded the loading message is replaced with the <Cart /> component as shown below.

Another way to do code splitting is to lazy load parts of your React component, as shown below.

tastics/cart/index.tsxtypescript
import React from 'react';
import { useCart } from 'frontastic/provider';
import Head from 'next/head';
import { useFormat } from 'helpers/hooks/useFormat';

import dynamic from 'next/dynamic';

const Cart = dynamic(() => import('components/commercetools-ui/cart'), {
  loading: () => <h1>Loading cart...</h1>,
});

const CartTastic = ({ data }) => {
  const { formatMessage } = useFormat({ name: 'cart' });
  const { data: cartList, removeItem, updateItem, shippingMethods } = useCart();
  const editItemQuantity = (lineItemId: string, newQuantity: number) =>
    updateItem(lineItemId, newQuantity);

  return (
    <>
      <Head>
        <title>
          {formatMessage({ id: 'checkout', defaultMessage: 'checkout' })}
        </title>
        <meta
          name="description"
          content={formatMessage({
            id: 'checkout',
            defaultMessage: 'checkout',
          })}
        />
      </Head>
      <Cart
        cart={cartList}
        removeItem={removeItem}
        editItemQuantity={editItemQuantity}
        shippingMethods={shippingMethods?.data}
        pageTitle={data.pageTitle}
        emptyStateImage={data.emptyStateImage}
        emptyStateTitle={data.emptyStateTitle}
        emptyStateSubtitle={data.emptyStateSubtitle}
        emptyStateCTALabel={data.emptyStateCTALabel}
        emptyStateCTALink={data.emptyStateCTALink}
      />
    </>
  );
};

export default CartTastic;