Next js에서 번들 크기를 줄이는 방법

발행: (2025년 12월 28일 오후 11:00 GMT+9)
8 min read
원문: Dev.to

Source: Dev.to

번역하려는 전체 텍스트를 제공해 주시면, 요청하신 대로 한국어로 번역해 드리겠습니다. 코드 블록, URL 및 마크다운 형식은 그대로 유지하겠습니다.

번들 크기가 중요한 이유

무거운 번들은 사용자가 앱과 상호작용하기도 전에 앱을 느리게 만듭니다.

  • 첫 로드가 느려짐: 브라우저가 JavaScript를 다운로드하고 파싱하는 데 시간이 더 오래 걸립니다.
  • 코어 웹 바이탈 감소: Google은 SEO 순위를 위해 성능을 중요하게 생각합니다.
  • 모바일 경험 악화: 느린 연결 환경에서는 큰 번들이 고통스럽습니다.

번들 크기를 줄이는 것은 사용자 만족도와 검색 순위에 직접적인 영향을 미칩니다.

Source:

Step 1: Analyze Your Bundle

블랜드를 무작정 최적화할 수는 없습니다. 먼저, 번들 안에 무엇이 들어 있는지 확인하세요.

@next/bundle-analyzer 사용하기:

npm install @next/bundle-analyzer

next.config.js 업데이트:

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

module.exports = withBundleAnalyzer({});

분석기 실행:

ANALYZE=true npm run build

번들의 트리맵이 생성됩니다.

**source-map-explorer**도 시도해 보세요 – 파일별로 번들 크기에 얼마나 기여하는지 시각화해 주는 또 다른 도구입니다.

목표는 수정하기 전에 가장 큰 문제 요소들을 파악하는 것입니다.

단계 2: 더 스마트하게 가져오기

전체 라이브러리를 가져와야 할 필요가 없는데 함수 하나나 두 개만 필요할 때 전체를 가져오는 실수를 흔히 저지릅니다.

Bad way:

import _ from 'lodash';
const result = _.isEmpty(obj);

Better way:

import isEmpty from 'lodash/isEmpty';
const result = isEmpty(obj);

두 번째 방법은 필요한 부분만 포함합니다. Next.js는 또한 트리‑쉐이킹과 next.config.jsoptimizePackageImports 옵션을 지원하여 라이브러리의 사용되지 않는 부분을 자동으로 제거합니다.

Step 3: 동적 임포트 사용

모든 코드를 첫 페이지 렌더링 시에 로드할 필요는 없습니다. 상호작용 후에만 사용된다면 나중에 로드하세요.

동적 컴포넌트 임포트:

import dynamic from 'next/dynamic';

const Chart = dynamic(() => import('../components/Chart'), {
  ssr: false,
  loading: () => <p>Loading...</p>,
});

이렇게 하면 차트 코드가 초기 번들에 포함되지 않습니다. 동적 임포트는 다음과 같은 경우에 적합합니다:

  • 모달
  • 차트 / 그래프
  • 서드파티 위젯
  • 거의 방문하지 않는 섹션

Step 4: 무거운 코드를 서버에 두기

Next.js는 서버와 클라이언트 코드를 분리합니다. 그 분리를 현명하게 활용하세요.

  • 데이터를 getServerSideProps 또는 getStaticProps에서 가져오고, 모든 것을 클라이언트에서 가져오지 마세요.
  • 브라우저에서 실행될 필요가 없는 로직은 Server Components(App Router)를 사용하세요.
  • 불필요한 비즈니스 로직을 클라이언트에 전달하지 마세요.

이렇게 하면 번들 크기가 줄어들고, 보안이 향상되며, 성능이 개선됩니다.

Step 5: Externalize or Replace Heavy Dependencies

Some libraries are simply too big. You have two choices: lazy‑load them or replace them.

  • Charts: Use a lighter charting library or load the heavy one on demand.
  • Date libraries: Replace Moment.js with Day.js or date‑fns.
  • React → Preact: Some projects swap React for Preact for smaller bundles (check compatibility first).

In next.config.js, you can also externalize server‑only packages so they don’t end up in the client bundle.

Step 6: Optimize Assets (Not Just JavaScript)

이미지, 폰트 및 CSS를 최적화하면 전체 성능이 향상됩니다.

  • Images: Next.js <Image> 컴포넌트를 사용하여 레이지 로딩, 압축 및 반응형 크기 조정을 적용합니다.
  • Fonts: 필요한 문자와 굵기만 가져오고, Google Fonts를 자체 호스팅하는 것을 고려합니다.
  • CSS: Tailwind의 purge 기능이나 기타 CSS 트리‑쉐이킹을 활성화하여 사용되지 않는 스타일을 제거합니다.

Step 7: 지속적인 모니터링

한 번 최적화하는 것만으로는 충분하지 않습니다. 새로운 의존성이나 기능이 추가될 때마다 무게가 늘어날 수 있습니다.

  • 예산 설정: size-limit와 같은 도구는 번들이 정의된 크기를 초과하면 경고합니다.
  • 분석기 재실행: 배포하기 전에 CI 워크플로의 일부로 포함시키세요.
  • 성능 추적: Lighthouse 점수, LCP(최대 콘텐츠 페인트), TTI(인터랙티브까지 시간)를 모니터링하세요.

빠른 체크리스트

  • @next/bundle-analyzer로 분석합니다.
  • 큰 의존성을 가벼운 대안으로 교체합니다.
  • 필요한 것만 가져옵니다.
  • 비핵심 UI에는 next/dynamic을 사용합니다.
  • 무거운 로직은 서버 측에 둡니다.
  • 이미지, 폰트, CSS를 최적화합니다.
  • 번들 크기를 지속적으로 모니터링합니다.

Final Thoughts

Next.js에서 번들 크기를 줄이는 것은 매 바이트마다 집착하는 것이 아니라, 실제로 중요한 것에 집중하는 것입니다: 더 빠른 로드 시간, 더 나은 SEO, 그리고 더 만족스러운 사용자. 큰 효과를 주는 것부터 시작하세요—컴포넌트를 지연 로드하고 의존성을 정리하는 것—그 다음에 import 최적화와 자산 처리로 미세 조정합니다. 이러한 관행을 적용하면 앱이 얼마나 부드럽고 반응성이 뛰어난지 뚜렷한 차이를 느낄 수 있을 것입니다.

Back to Blog

관련 글

더 보기 »

🚀 번들 사이즈를 죽이는 걸 멈춰라

자동으로 TypeScript에서 Barrel 파일 제거하기! 커버 이미지 설명: 왼쪽에 무겁고 뒤얽힌 번들이 표시되고, 오른쪽에 깔끔하고 직접적인 import가 표시된 분할 화면.