
Next.js ์ฑ์์ ์๋ฒ ์์ ์์ ์ ๋ฑ ํ ๋ฒ๋ง ์คํ๋๋ ์ด๊ธฐํ ๋ก์ง์ด ํ์ํ๋ค. ๋ฐ์ดํฐ๋ฒ ์ด์ค ์ฐ๊ฒฐ, ์บ์ ์ค์ , ์ธ๋ถ ์๋น์ค ์ฐ๊ฒฐ ๊ฐ์ ๊ฒ๋ค ๋ง์ด๋ค. ๊ณต์ ๋ฌธ์๋ฅผ ๋ณด๋ instrumentation.ts ํ์ผ์ ๋ง๋ค๋ฉด ์ฑ ์์ ์์ ์ ํ ๋ฒ ๋์๊ฐ๋ ๊ธฐ๋ฅ์ด ์์๊ณ register ํจ์๋ฅผ exportํ๋ฉด ๋๋ค๊ณ ๋์์์๋ค.
// instrumentation.ts
export async function register() {
console.log('์๋ฒ ์ด๊ธฐํ ์ค...');
// ์ด๊ธฐํ ๋ก์ง
}
๊ฐ๋ฐ ํ๊ฒฝ์์๋ ์ ๋๋๋ผ. npm run dev ํ๋ฉด ์ฝ์์ ๋ก๊ทธ๋ ์ ์ฐํ๊ณ , ์ด๊ธฐํ๋ ์ ์์ ์ผ๋ก ์คํ๋๋ค. ๊ทธ๋ฐ๋ฐ ํ๋ก๋์
๋น๋ ํ ์คํํ๋๊น ์๋ฌด๊ฒ๋ ์ ๋๋ค.
npm run build
npm start
์ฝ์์ ์๋ฌด๋ฐ ๋ก๊ทธ๋ ์๊ณ , ์ด๊ธฐํ ์ฝ๋๋ ์คํ๋์ง ์์๋ค. ๋ญ๊ฐ ์ด์ํด์ GitHub ์ด์๋ค์ ์ฐพ์๋ดค๋๋ ๋๋ง ๊ฒช๋ ๋ฌธ์ ๊ฐ ์๋์๋ค.
๋ฐ๊ฒฌํ ์ด์๋ค
Next.js ๊ณต์ ๋ ํฌ์งํ ๋ฆฌ์์ ๊ด๋ จ ์ด์๋ค์ ์ฌ๋ฌ ๊ฐ ๋ฐ๊ฒฌํ๋ค.
ํนํ Next.js 14.0.5-canary.29์์ ๋ฐ๊ฒฌํ ๊ฑด๋ฐ, ํ๋ก๋์ ๋น๋ ํ ์๋ฒ๋ฅผ ์์ํ ๋ register ํจ์๊ฐ ์๋์ผ๋ก ํธ์ถ๋์ง ์๊ณ , ์ฒซ ๋ฒ์งธ ๋ผ์ฐํธ๋ฅผ ๋ฐฉ๋ฌธํด์ผ๋ง ์คํ๋๋ ๋ฌธ์ ์๋ค. ํ์ง๋ง ๋๋ Next.js 15๋ฅผ ์ฌ์ฉํ๊ณ , instrumentation ๊ธฐ๋ฅ์ด ์ ์์ผ๋ก ์์ ํ๋์ด์ experimental.instrumentationHook ์ค์ ์ config์ ์์ฑํ์ง ์์๋ ๊ธฐ๋ณธ์ ์ผ๋ก ๋์ํ๋ค.
์ด ๊ธฐ๋ฅ ์์ฒด๊ฐ ์ฑ๋ฅ ์ถ์ ์ด๋ ๋๋ฒ๊น , ๊ด์ฐฐ ๊ฐ๋ฅ์ฑ ๋๊ตฌ ํตํฉ ๋ชฉ์ ์ผ๋ก ๋ง๋ค์ด์ง ๊ฑฐ๋ผ ์ด๋ ์ ๋๋ ์์๋ ๋์์ด๋ผ๊ณ ์๊ฐํ๋ค.
๋ฌธ์ ๋ ์๋ฒ ์์๊ณผ ๋์์ ์คํ๋์ด์ผ ํ ์ด๊ธฐํ ๋ก์ง์ด ์ฌ์ฉ์์ ์ฒซ ๋ฒ์งธ HTTP ์์ฒญ์ ์์กดํ๋ค๋ ์ ์ด์๋ค. ์๋ฒ๊ฐ ์์๋์๋ง์ ๋ฐ์ดํฐ๋ฒ ์ด์ค ์ฐ๊ฒฐ์ด๋ ํ๊ฒฝ ์ค์ ๊ฐ์ ๊ฑธ ์ด๊ธฐํํด์ผ ํ๋๋ฐ, ๋๊ตฐ๊ฐ ์น์ฌ์ดํธ์ ์ ์ํด์ผ๋ง ๊ทธ ์ฝ๋๊ฐ ๋์๊ฐ๋ค๋... ๊ฒฐ๊ตญ ๋ค๋ฅธ ๋ฐฉ๋ฒ์ ์ฐพ์์ผ ํ๋ค.
ํด๊ฒฐ์ฑ ์ฐพ๊ธฐ
instrumentation ๊ธฐ๋ฅ ์์ฒด๊ฐ ๋ถ์์ ํ๊ณ , next ํ์์๋ ๋์ ๋ฐฉ์์ ๋ธ๋ ๋ฐ์ค๋ก ์จ๊ฒจ๋์ผ๋ ๋ค๋ฅธ ๋ฐฉ๋ฒ์ ์จ์ผ๊ฒ ๋ค๊ณ ์๊ฐํ๋ค. ์ฌ๋ฌ ๋ฐฉ๋ฒ์ ์๋ํด๋ดค๋๋ฐ, ๊ฐ๊ฐ ์ฅ๋จ์ ์ด ์์๋ค.
1. Next.js ์ปค์คํ ์๋ฒ
๊ฐ์ฅ ํ์คํ ๋ฐฉ๋ฒ์ Next.js ๋ด์ฅ ์ปค์คํ ์๋ฒ๋ฅผ ์ฌ์ฉํ๋ ๊ฒ์ด๋ค.
// server.js
const { createServer } = require('http');
const { parse } = require('url');
const next = require('next');
const dev = process.env.NODE_ENV !== 'production';
const app = next({ dev });
const handle = app.getRequestHandler();
async function initialize() {
console.log('๐ ์๋ฒ ์ด๊ธฐํ ์ค...');
// ์ฌ๊ธฐ์ ์ด๊ธฐํ ๋ก์ง ์์ฑ
// await connectDatabase();
// await setupCache();
console.log('โ
์ด๊ธฐํ ์๋ฃ');
}
app.prepare().then(async () => {
await initialize();
createServer((req, res) => {
const parsedUrl = parse(req.url, true);
handle(req, res, parsedUrl);
}).listen(3000, () => {
console.log('> Ready on http://localhost:3000');
});
});
package.json์์ start ์คํฌ๋ฆฝํธ๋ ๋ฐ๊ฟ์ค๋ค:
{
"scripts": {
"start": "node server.js"
}
}
์ด๋ ๊ฒ ํ๋ฉด Next.js ์๋ฒ๊ฐ ์ค๋น๋ ์งํ์ ์ด๊ธฐํ ํจ์๊ฐ ํ์คํ ์คํ๋๋ค.
2. ๋ชจ๋ ๋ ๋ฒจ์์ ์คํ
์ข ๋ ๊ฐ๋จํ ๋ฐฉ๋ฒ๋ ์๋ค. Next.js ์ฑ ๋ด์์ ๋ชจ๋์ด ์ฒ์ ๋ก๋๋ ๋ ์ด๊ธฐํํ๋ ๋ฐฉ์์ด๋ค.
// lib/server-init.ts
let initialized = false;
async function initializeApp() {
if (initialized) return;
console.log('๐ ์ฑ ์ด๊ธฐํ ์ค...');
// ์ด๊ธฐํ ๋ก์ง
initialized = true;
console.log('โ
์ฑ ์ด๊ธฐํ ์๋ฃ');
}
// ์๋ฒ์์๋ง ์คํ
if (typeof window === 'undefined') {
initializeApp();
}
๊ทธ๋ฆฌ๊ณ app/layout.tsx์์ ์ด ๋ชจ๋์ import๋ง ํด์ฃผ๋ฉด ๋๋ค.
// app/layout.tsx
import '@/lib/server-init'; // ์ด๊ฒ๋ง ์ถ๊ฐ
export default function RootLayout({
children,
}: {
children: React.ReactNode;
}) {
return (
<html>
<body>{children}</body>
</html>
);
}
3. ์ข ๋ ์ ๊ตํ ์กฐ๊ฑด ์ฒ๋ฆฌ
๋น๋ ํ์๊ณผ ๋ฐํ์์ ํ์คํ ๊ตฌ๋ถํ๊ณ ์ถ๋ค๋ฉด ์ด๋ฐ ๋ฐฉ๋ฒ๋ ์๋ค.
// ๋ฐํ์์์๋ง ์คํ (๋น๋ ํ์ ์ ์ธ)
if (
typeof window === "undefined" &&
process.env.NEXT_PHASE !== "phase-production-build" &&
process.env.NEXT_PHASE !== "phase-export" &&
!process.env.NEXT_BUILD_ID
) {
process.nextTick(() => {
initializeApp().catch((error) => {
console.error("์ฑ ์ด๊ธฐํ ์ค ์ค๋ฅ ๋ฐ์:", error);
});
});
}
์ด๋ ๊ฒ ํ๋ฉด Next.js๊ฐ ๋น๋ ์ค์ผ ๋๋ ์คํ๋์ง ์๊ณ , ์ค์ ์๋ฒ๊ฐ ๋์๊ฐ ๋๋ง ์คํ๋๋ค.
์ด ๋ฐฉ๋ฒ์ด ์ต์ด 1๋ฒ๋ง ์คํ๋๋ ์ด์ ๋ Node.js์ ๋ชจ๋ ์บ์ฑ ์์คํ ๋๋ฌธ์ด๋ค. Node.js๋ ํ ๋ฒ ๋ก๋๋ ๋ชจ๋์ ๋ฉ๋ชจ๋ฆฌ์ ์บ์ํด๋๊ณ , ๊ฐ์ ๋ชจ๋์ ๋ค์ importํ ๋๋ ์๋ก ์คํํ์ง ์๊ณ ์บ์๋ ๊ฒฐ๊ณผ๋ฅผ ์ฌ์ฌ์ฉํ๋ค. ๋ฐ๋ผ์ lib/server-init.ts ํ์ผ์ด ์ฒ์ import๋ ๋๋ง ์ต์์ ๋ ๋ฒจ์ ์ฝ๋๊ฐ ์คํ๋๊ณ , ๊ทธ ์ดํ์๋ ์๋ฌด๋ฆฌ ๋ง์ ์ปดํฌ๋ํธ์์ ์ด ๋ชจ๋์ importํด๋ ์ด๊ธฐํ ์ฝ๋๋ ๋ค์ ์คํ๋์ง ์๋๋ค.
์ด๋ RSC(React Server Components)์๋ ์ง์ ์ ์ธ ๊ด๋ จ์ด ์๋, Node.js ์์ฒด์ ๊ธฐ๋ณธ ๋์์ด๋ค. ๋ค๋ง Next.js App Router ํ๊ฒฝ์์๋ layout.tsx์์ ๋ชจ๋์ importํ ๋ ์๋ฒ์์ ๋ ๋๋ง๋๋ฉด์ ์ด๊ธฐํ๊ฐ ์คํ๋๋ ๊ฒ๋ฟ์ด๋ค. ์ฌ๊ธฐ์ initialized ํ๋๊ทธ๋ฅผ ์ถ๊ฐ๋ก ์ฌ์ฉํด์ ํน์ ๋ชจ๋ฅผ ์ค๋ณต ์คํ๋ ๋ฐฉ์งํ๊ณ , typeof window === 'undefined' ์ฒดํฌ๋ก ์๋ฒ ํ๊ฒฝ์์๋ง ์คํ๋๋๋ก ๋ณด์ฅํ๋ ์ด์ค ์์ ์ฅ์น๋ฅผ ๋ง๋ จํ ์ ์ด๋ค.
๊ฒฐ๋ก
Next.js 15์์ instrumentation.ts๋ ๊ฐ๋ฐ ํ๊ฒฝ์์๋ ์ ๋์ง๋ง ํ๋ก๋์
์์๋ ์ ๋ขฐํ ์ ์๋ค. ํนํ standalone ๋น๋๋ Docker ํ๊ฒฝ์์๋ ๋๋์ฑ ๊ทธ๋ ๋ค. ๋น๋ถ๊ฐ์ ์ปค์คํ
์๋ฒ๋ฅผ ์ฌ์ฉํ๊ฑฐ๋ ๋ชจ๋ ๋ ๋ฒจ์์ ์ด๊ธฐํํ๋ ๋ฐฉ์์ ์ฐ๋ ๊ฒ ์ข๊ฒ ๋ค. ๊ฐ์ธ์ ์ผ๋ก๋ ์ปค์คํ
์๋ฒ ๋ฐฉ์์ ์ถ์ฒํ๋ค. ์ข ๋ ๋ช
์์ ์ด๊ณ ์ ์ด ๊ฐ๋ฅํ๊ธฐ ๋๋ฌธ์ด๋ค. ์ด์ฐจํผ ํ๋ก๋์
์์๋ ํ์คํ ๊ฒ ์ต๊ณ ๋ค.
'๐ Front > โ๏ธ React JS' ์นดํ ๊ณ ๋ฆฌ์ ๋ค๋ฅธ ๊ธ
| Tailwind v4 ๋์ ํ๋ค๊ฐ monorepo ๋น๋ ์์คํ ์ ๋ฏ์ด๊ณ ์น ์ฐ (2) | 2025.06.01 |
|---|---|
| React-19 useActionState ์ดํด๋ณด๊ธฐ (0) | 2024.05.26 |
| [React] ๊น๋นก์ ํ์ ํด๊ฒฐ (useLayoutEffect, APIํธ์ถ) (0) | 2022.03.30 |
| virtual DOM ํํค์น๊ธฐ (0) | 2021.12.09 |
| React [๋ฆฌ๋ ๋๋ง ๊ณผ์ ] (0) | 2021.09.08 |