| 일 | 월 | 화 | 수 | 목 | 금 | 토 |
|---|---|---|---|---|---|---|
| 1 | 2 | 3 | 4 | 5 | 6 | |
| 7 | 8 | 9 | 10 | 11 | 12 | 13 |
| 14 | 15 | 16 | 17 | 18 | 19 | 20 |
| 21 | 22 | 23 | 24 | 25 | 26 | 27 |
| 28 | 29 | 30 |
Tags
- 개발자
- 크래프톤 정글
- 정렬
- 프론트엔드
- 혼자 공부해서 개발까지
- 알고리즘
- Mini-React
- Python
- frontend
- react
- 프론트앤드
- HTML기초
- 알고리즘 기초
- 그래프
- DFS
- CSS
- js
- 그리디
- Git
- c언어
- html
- 프로그래머스
- BFS
- 코딩테스트
- 코딩
- 해시
- 백준
- javascript
- 팀프로젝트
- 정글
Archives
- Today
- Total
민혁이의 IT스토리
서버 컴포넌트 vs 클라이언트 컴포넌트 본문
1. 기본 개념 및 실행 환경
가장 큰 차이점은 코드가 실행되는 환경입니다.
| 구분 | 서버 컴포넌트 (Server Component) | 클라이언트 컴포넌트 (Client Component) |
| 실행 환경 | 서버 (Node.js 런타임) | 클라이언트 (브라우저) |
| 기본 설정 | App Router의 기본값 | 컴포넌트 최상단에 "use client"; 명시 |
| 자바스크립트 번들 | 클라이언트에 전송되지 않음 (JS 번들 크기 감소) | 클라이언트에 전송되고 실행됨 (상호작용 담당) |
| 렌더링 과정 | 서버에서 HTML로 미리 렌더링되어 전송 | 브라우저에서 HTML을 받은 후 하이드레이션(Hydration) 과정을 거쳐 상호작용 가능 |
2. 주요 역할 및 사용처
각 컴포넌트 타입은 고유의 장점을 살려 애플리케이션의 특정 부분을 담당합니다.
서버 컴포넌트 (Server Component)의 역할
- 데이터 패칭 (Data Fetching): 데이터베이스나 API 서버에 가장 가까운 곳인 서버에서 데이터를 직접 가져옵니다. 네트워크 지연 시간을 줄여 성능을 향상시킵니다.
- 예시: async/await를 사용하여 컴포넌트 내에서 직접 fetch를 수행.
- 민감한 정보 관리: API 키, 토큰, 환경 변수 등 민감한 정보를 클라이언트에 노출하지 않고 서버에서 안전하게 사용합니다.
- 번들 크기 최소화: 클라이언트 JS 번들에 포함되지 않으므로, 정적 콘텐츠나 무거운 라이브러리를 사용할 때 번들 크기를 크게 줄여줍니다.
- SEO 및 초기 로딩 성능 개선: 서버에서 완전히 렌더링된 HTML을 전송하여 FCP (First Contentful Paint) 속도를 높이고 SEO에 유리합니다.
- 사용 예시: 정적 레이아웃, 블로그 글 본문, 제품 목록 표시, 데이터베이스 쿼리 로직.
클라이언트 컴포넌트 (Client Component)의 역할
- 상태(State) 및 라이프사이클 관리: useState, useReducer, useEffect와 같은 React Hooks를 사용하여 컴포넌트의 상태를 관리하고 라이프사이클에 따른 로직을 실행합니다.
- 사용자 상호작용 (Interactivity): onClick, onChange와 같은 이벤트 핸들러를 사용하여 사용자 입력 및 동적인 UI 처리를 담당합니다.
- 브라우저 전용 API 사용: window, document, localStorage 등 브라우저 환경에서만 접근 가능한 API를 사용합니다.
- 사용 예시: 카운터 버튼, 입력 폼, 모달, 애니메이션, 클라이언트 측 상태 관리 라이브러리 (Redux, Zustand) 연동.
3. 서버 컴포넌트와 클라이언트 컴포넌트의 공존 (Composition)
Next.js App Router의 진정한 강점은 이 두 컴포넌트를 혼합하여 사용할 수 있다는 점입니다.
- 서버 컴포넌트가 클라이언트 컴포넌트를 포함:
- 가장 일반적인 패턴입니다. 서버 컴포넌트가 데이터를 패칭하고, 그 데이터를 props로 클라이언트 컴포넌트에 전달하여 상호작용이 필요한 부분을 렌더링합니다.
- 예시: 서버 컴포넌트가 전체 페이지 레이아웃과 제품 목록 데이터를 가져오고, 클라이언트 컴포넌트인 <AddToCartButton />을 목록 내부에 사용합니다.
- 클라이언트 컴포넌트 내부에 서버 컴포넌트 삽입 (권장되지 않음):
- 클라이언트 컴포넌트는 서버 컴포넌트를 직접 import할 수 없습니다. 이는 빌드 에러를 유발합니다.
- 하지만, 클라이언트 컴포넌트의 children prop으로 서버 컴포넌트를 전달하는 것은 가능합니다. 이 경우, 서버 컴포넌트는 서버에서 렌더링을 완료한 후 그 결과(HTML/RSC Payload)가 클라이언트 컴포넌트에게 전달됩니다. 이를 통해 '클라이언트 컴포넌트 아래에 서버 컴포넌트'를 배치하는 효과를 낼 수 있습니다.
- Best Practice: 클라이언트 컴포넌트는 상호작용이 필요한 최소한의 영역을 담당하도록 컴포넌트 트리의 가장 아래(leaves)에 배치하는 것이 좋습니다. 이를 통해 클라이언트 번들 크기를 최소화할 수 있습니다.
4. 요약 및 최적화 전략
| 구분 | 서버 컴포넌트 | 클라이언트 컴포넌트 |
| 최상단 지시어 | 없음 (기본값) | "use client"; |
| 사용 가능 API | 서버 API (fs, headers, 데이터베이스 직접 접근) | 브라우저 API (window, document, localStorage) |
| Hooks | 사용 불가능 | useState, useEffect 등 사용 가능 |
| 데이터 패칭 | 서버에서 직접 처리 (빠름, 보안 우수) | useEffect나 클라이언트 라이브러리로 클라이언트에서 비동기 처리 |
| 장점 | 초기 로딩 속도, SEO, 보안, 번들 크기 | 동적인 UI, 사용자 상호작용, 상태 관리 |
'혼자 공부해서 개발까지 > Next.js' 카테고리의 다른 글
| 컴포넌트 렌더링 3가지 방식 (0) | 2025.12.18 |
|---|