🚀 CodeAudit.dev is launching soon. Join the Waitlist →
[ BACK TO SYSTEM.LOG ]
PerformanceTTR: 8 min readJune 2, 2026

How to Reduce JavaScript Bundle Size in Next.js

Is your Next.js application suffering from slow load times? Learn actionable strategies to analyze and significantly reduce your JavaScript bundle size.

Next.js provides a fantastic developer experience, but if you aren't careful, it's incredibly easy to ship massive JavaScript bundles to your users. Large bundles lead to slow Time to Interactive (TTI), poor Core Web Vitals, and frustrated users on mobile devices.

Here is a comprehensive guide to identifying bundle bloat and fixing it in your Next.js application.

1. Analyze Your Current Bundle

You cannot fix what you cannot measure. The first step is to see exactly what is taking up space.

Install the @next/bundle-analyzer package:

bash
npm install @next/bundle-analyzer

Update your next.config.js:

javascript
const withBundleAnalyzer = require('@next/bundle-analyzer')({
  enabled: process.env.ANALYZE === 'true',
});
module.exports = withBundleAnalyzer({});

Run the analyzer:

bash
ANALYZE=true npm run build
This will open a visual treemap in your browser. Look for massive colored blocks. Common offenders include lodash, moment, framer-motion, and large UI libraries.

2. Dynamic Imports for Heavy Components

If a component is not needed on the initial page load (e.g., a modal, a complex chart, or a heavy rich-text editor), do not include it in the main bundle. Use Next.js dynamic imports.

javascript
import dynamic from 'next/dynamic'

// This component will only be loaded when it is rendered
const HeavyChart = dynamic(() => import('../components/HeavyChart'), {
  loading: () => 

Loading chart...

, ssr: false // Optional: disable server-side rendering if it relies on browser APIs })

3. Replace Heavy Dependencies

Many popular libraries have modern, lightweight alternatives.

  • Replace Moment.js (massive, mutable) with date-fns or Day.js.
  • Replace full Lodash imports (import _ from 'lodash') with specific function imports (import get from 'lodash/get'), or use native JavaScript array/object methods.
  • If you only use one icon from a massive icon library, ensure you are importing it directly rather than pulling in the entire set.
  • 4. Leverage React Server Components (App Router)

    If you are using the Next.js App Router, take full advantage of React Server Components (RSC).

    By default, components in the app directory are Server Components. Their dependencies are never sent to the client bundle. Only add the "use client" directive when you absolutely need interactivity (hooks, state, or event listeners).

    Push interactivity down the tree. Don't make an entire page a Client Component just because you need a button to track state; extract the button into its own Client Component and keep the rest of the page server-rendered.

    5. Optimize Third-Party Scripts

    Marketing tags, analytics, and customer support widgets can ruin your performance.

    Always use the Next.js Script component instead of raw