Post

Nextjs-Optimizing(2) - Package Bundling

๐Ÿ“Œ์‹œ์ž‘ํ•˜๋ฉฐ

15.2.2 ๊ณต์‹๋ฌธ์„œ ๊ธฐ๋ฐ˜์œผ๋กœ ์ž‘์„ฑ

์•„์ง ์ž‘์—…์ด ์™„์ „ํžˆ ๋๋‚œ ๊ฒƒ์€ ์•„๋‹ˆ์ง€๋งŒ, ๊ณต์‹๋ฌธ์„œ๋ฅผ ๋ณด๋ฉด์„œ ๊พธ์ค€ํžˆ Next.js์˜ ์ตœ์ ํ™” ๊ธฐ๋ฒ•์— ๋Œ€ํ•ด์„œ ๊ด€์‹ฌ์„ ๊ฐ€์ง€๊ณ  ์žˆ๋‹ค!

ํŠน์ • <Image> ์ปดํฌ๋„ŒํŠธ๋‚˜, <Scripts> ๊ฐ™์€ ๊ฒฝ์šฐ์—๋Š” ์ง์ ‘ ์˜ˆ์ œ๋ฅผ ๋งŒ๋“ค์–ด ๋ณด๋ฉด์„œ ํ•™์Šตํ•˜๋Š” ์ค‘์ด๋ผ ๋ธ”๋กœ๊ทธ์— ์ •๋ฆฌํ•˜๋Š”๊ฑด ์กฐ๊ธˆ ์‹œ๊ฐ„์ด ๊ฑธ๋ฆด ๊ฒƒ ๊ฐ™์•„ Package Bundling ๋ถ€๋ถ„๋ถ€ํ„ฐ ์‚ดํŽด๋ณด๊ณ ์ž ํ•œ๋‹ค.

1๏ธโƒฃAnalyzing JavaScript bundles

@next/bundle-analyzer๋Š” ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜ ๋ฒˆ๋“ค ํฌ๊ธฐ๋ฅผ ๊ด€๋ฆฌํ•˜๋Š”๋ฐ ๋„์›€์„ ์ฃผ๋Š” Next.js์˜ ํ”Œ๋Ÿฌ๊ทธ์ธ์ด๋‹ค. ์ด ํ”Œ๋Ÿฌ๊ทธ์ธ์„ ํ†ตํ•ด ๊ฐ ํŒจํ‚ค์ง€์˜ ํฌ๊ธฐ์™€ ์ข…์†์„ฑ์„ ์‹œ๊ฐ์ ์œผ๋กœ ํ™•์ธํ•  ์ˆ˜ ์žˆ๊ณ , ์ด ์ •๋ณด๋ฅผ ๊ธฐ๋ฐ˜์œผ๋กœ ์•„๋ž˜์™€ ๊ฐ™์€ ์ตœ์ ํ™”๋ฅผ ์ง„ํ–‰ํ•  ์ˆ˜ ์žˆ๋‹ค.

  • ํฐ ์‚ฌ์ด์ฆˆ dependencies(์ข…์†์„ฑ) ์ œ๊ฑฐ
  • ์ฝ”๋“œ ๋ถ„ํ• 
  • lazy load(์ง€์—ฐ ๋กœ๋“œ)

๐Ÿงก์„ค์น˜ํ•˜๊ธฐ

1
2
3
4
5
npm i @next/bundle-analyzer
# or
yarn add @next/bundle-analyzer
# or
pnpm add @next/bundle-analyzer

์„ค์น˜๊ฐ€ ์™„๋ฃŒ๋˜๋ฉด next.config.js์— ๋‹ค์Œ๊ณผ ๊ฐ™์ด ์ž‘์„ฑํ•œ๋‹ค.

1
2
3
4
5
6
7
8
/** @type {import('next').NextConfig} */
const nextConfig = {}

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

module.exports = withBundleAnalyzer(nextConfig)

+ ๊ณต์‹๋ฌธ์„œ์—์„œ๋Š” CommonJS(.cjs) ๋ฐฉ์‹์œผ๋กœ ์ž‘์„ฑ๋˜์–ด ์žˆ์œผ๋‚˜, ๋‚˜๋Š” ES Module ๋ฐฉ์‹์ธ next.config.mjs๋ฅผ ์‚ฌ์šฉํ•˜๊ณ  ์žˆ์–ด ์˜ค๋ฅ˜๊ฐ€ ๋ฐœ์ƒํ–ˆ๋‹ค. ๋”ฐ๋ผ์„œ ์•„๋ž˜์™€ ๊ฐ™์ด ์ž‘์„ฑํ•ด์ฃผ์—ˆ๋‹ค.

1
2
3
4
5
6
/** @type {import('next').NextConfig} */
import bundleAnalyzer from "next-bundle-analyzer"

const withBundleAnalyzer = bundleAnalyzer({
  enabled: process.env.ANALYZE === "true",
})

โœจ์•Œ์•„๋‘๊ธฐ .cjs โ†’ CommonJS ๋ฐฉ์‹ (require, module.exports) .mjs โ†’ ES ๋ชจ๋“ˆ ๋ฐฉ์‹ (import, export default)

๐Ÿ’›๋ณด๊ณ ์„œ ์ƒ์„ฑํ•˜๊ธฐ

1
2
3
4
5
ANALYZE=true npm run build
# or
ANALYZE=true yarn build
# or
ANALYZE=true pnpm build

๋ช…๋ น์–ด๋ฅผ ์‹คํ–‰ํ•ด์ฃผ๋ฉด, ๋‚ด๊ฐ€ ๋งŒ๋“  ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์˜ ํŠธ๋ฆฌ๋งต ์ฐจํŠธ๋ฅผ ํ™•์ธํ•  ์ˆ˜ ์žˆ๋‹ค! ํŒŒ์ผ ํฌ๊ธฐ์™€ ๊ตฌ์กฐ๋ฅผ ํ•œ๋ˆˆ์— ํŒŒ์•…ํ•  ์ˆ˜ ์žˆ์–ด, ๋‚ด๊ฐ€ ์–ด๋–ค ํŒŒ์ผ์„ ์ค„์ผ ์ˆ˜ ์žˆ๋Š”์ง€ ํŒŒ์•…ํ•˜๋Š”๋ฐ ๋„์›€์„ ์ค€๋‹ค.๐Ÿ˜Ž


2๏ธโƒฃOptimizing package imports

์•„์ด์ฝ˜ ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ์™€ ๊ฐ™์€ ์ผ๋ถ€ ํŒจํ‚ค์ง€๋“ค์€ ์ˆ˜๋ฐฑ ๊ฐœ์˜ ๋ชจ๋“ˆ์„ ๋‚ด๋ณด๋‚ผ ์ˆ˜ ์žˆ์–ด ๊ฐœ๋ฐœ ํ˜น์€ ํ”„๋กœ๋•์…˜์—์„œ ์„ฑ๋Šฅ ๋ฌธ์ œ๋ฅผ ์ผ์œผํ‚ฌ ์ˆ˜ ์žˆ๋‹ค.

์ด๋Ÿฐ ํŒจํ‚ค์ง€๋ฅผ import ํ•˜๋Š” ๋ฐฉ์‹์„ ์ตœ์ ํ™” ํ•˜๊ธฐ ์œ„ํ•ด์„œ optimizePackageImports ์˜ต์…˜์„ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ๋‹ค. ์ด ์˜ต์…˜์„ ์‚ฌ์šฉํ•˜๋ฉด ์‹ค์ œ๋กœ ์‚ฌ์šฉํ•˜๋Š” ๋ชจ๋“ˆ๋งŒ ๋กœ๋“œํ•˜๊ฒŒ ๋œ๋‹ค.

1
2
3
4
5
6
7
8
/** @type {import('next').NextConfig} */
const nextConfig = {
  experimental: {
    optimizePackageImports: ["icon-library"],
  },
}

module.exports = nextConfig

โœจ์•Œ์•„๋‘๊ธฐ Next.js๋Š” ์ผ๋ถ€ ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ๋ฅผ ์ž๋™์œผ๋กœ ์ตœ์ ํ™”ํ•˜๊ธฐ๋•Œ๋ฌธ์— ํ•ด๋‹น ์˜ต์…˜์„ ์‚ฌ์šฉํ•˜์ง€ ์•Š์•„๋„ ๋˜๋Š” ๊ฒฝ์šฐ๊ฐ€ ์žˆ๋‹ค. ๊ทธ ๋ชฉ๋ก์€ ์ด์ชฝ์„ ์ฐธ์กฐํ•œ๋‹ค.


3๏ธโƒฃOpting specific packages out of bundling

์„œ๋ฒ„ ์ปดํฌ๋„ŒํŠธ์™€ ๋ผ์šฐํŠธ ํ•ธ๋“ค๋Ÿฌ ๋‚ด๋ถ€์—์„œ ๊ฐ€์ ธ์˜จ ํŒจํ‚ค์ง€๋Š” Next.js์— ์˜ํ•ด ์ž๋™์œผ๋กœ ๋ฒˆ๋“ค๋กœ ์ œ๊ณต๋œ๋‹ค. ๋งŒ์•ฝ ์ด๋ฅผ ์›์น˜ ์•Š๋Š”๋‹ค๋ฉด, serverExternalPackages ์˜ต์…˜์„ ์‚ฌ์šฉํ•ด ์„œ๋ฒ„์ธก์—์„œ๋งŒ ์‚ฌ์šฉํ•˜๋Š” ํŒจํ‚ค์ง€๋ฅผ ํด๋ผ์ด์–ธํŠธ ๋ฒˆ๋“ค์—์„œ ์ œ์™ธํ•˜๋„๋ก ํ•ด ์ตœ์ ํ™” ํ•  ์ˆ˜ ์žˆ๋‹ค.

1
2
3
4
5
6
/** @type {import('next').NextConfig} */
const nextConfig = {
  serverExternalPackages: ["package-name"], // 'package-name'์„ ๋ฒˆ๋“ค์—์„œ ์ œ์™ธ
}

module.exports = nextConfig

๐Ÿ“š๋ฐฐ์šด์ 

์ค‘๊ฐ„์ ๊ฒ€์œผ๋กœ ํ˜„์žฌ ์—…๋ฌด์—์„œ ์ž‘์—…ํ•˜๋Š” ํ”„๋กœ์ ํŠธ์— ํ•ด๋‹น ์˜ต์…˜์„ ์ ์šฉํ•ด์„œ ์–ด๋–ค ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ๊ฐ€ ์‚ฌ์šฉ๋˜๊ณ , ์–ด๋А ์ •๋„์˜ ์‚ฌ์ด์ฆˆ๋ฅผ ์ฐจ์ง€ํ•˜๋Š”์ง€ ํ™•์ธํ•ด๋ณด์•˜๋‹ค!

์ƒ๊ฐ๋ณด๋‹ค ์‚ฌ์ด์ฆˆ๊ฐ€ ํฐ ๊ฒƒ์ด ๋ช‡๊ฐœ ๋ณด์˜€๋Š”๋ฐ, ๋งŽ์€ ์ปดํฌ๋„ŒํŠธ์—์„œ ํ•„์ˆ˜์ ์œผ๋กœ ์‚ฌ์šฉํ•˜๋Š” ๊ธฐ๋Šฅ์ด ์•„๋‹ˆ์—ˆ๊ธฐ ๋•Œ๋ฌธ์— ํ•ด๋‹น ๋ถ€๋ถ„์€ ๋‚ด๊ฐ€ ์ง์ ‘ ๊ตฌํ˜„ํ•˜๋Š” ๊ฒƒ์œผ๋กœ ๋ฆฌํŒฉํ† ๋งํ•˜๋ฉด์„œ ์‚ฌ์ด์ฆˆ๋ฅผ ๋งŽ์ด ์ค„์ผ ์ˆ˜ ์žˆ์—ˆ๋‹ค.

Next.js ๊ณต์‹๋ฌธ์„œ์—์„œ ์–˜๊ธฐํ•˜๋Š” ๊ฒƒ ์ฒ˜๋Ÿผ ์–ด๋–ค ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ๋ฅผ ๋„์ž…ํ•  ๋•Œ, ํ˜น์€ ์ž‘์—… ์ค‘์— ๋‚ด๊ฐ€ ๋งŒ๋“  ์ปดํฌ๋„ŒํŠธ๊ฐ€ ์–ด๋А์ •๋„ ์‚ฌ์ด์ฆˆ๋ฅผ ์ฐจ์ง€ํ•˜๊ณ  ์ด๊ฒŒ ๋‚ด ํ”„๋กœ์ ํŠธ์— ์–ด๋А ์ •๋„์˜ ์˜ํ–ฅ์„ ๋ฏธ์น  ์ˆ˜ ์žˆ๋Š”์ง€๋ฅผ ํŒ๋‹จํ•˜๋ฉฐ ์ž‘์—…ํ•˜๋ฉด ํ›จ์”ฌ ์พŒ์ ํ•œ ๊ฒฐ๊ณผ๋ฌผ์ด ๋  ์ˆ˜ ์žˆ์œผ๋ฆฌ๋ผ ์ƒ๊ฐํ•œ๋‹ค.๐Ÿ˜Š

๐Ÿ—‚๏ธ์ฐธ๊ณ  ์‚ฌ์ดํŠธ

This post is licensed under CC BY 4.0 by the author.