Server Component vs Client Component

YJ·2025년 11월 11일
0

이번에도 next.js 공식 문서를 공부하다가 데리고 왔다.
서버, 클라이언트 컴포넌트에 대해 조금 더 심층 공부해볼 예정 !

지금까지 프론트 공부하면서 매 시간마다 본

서버 vs 클라이언트 구조

⬇️ 얘는 SEO 관련 세미나 준비 때 봤던 거 같고
- Server Side Rendering (SSR) vs Client Side Rendering (CSR)

⬇️ 얘는 오늘 next.js 공식문서에서 처음 봤다
- Server Component vs Client Component

 

둘이 똑같은 건 줄 알았는데 조금은 차이점이 있다고 한다?
(참고1 : https://f-lab.kr/insight/react-server-components-vs-ssr?gad_source=1&gclid=Cj0KCQjwsaqzBhDdARIsAK2gqnemvky3_9cOzvW3gRByc0bTPskIFKZnUPazRkcX6YrI5_zmkk-HOpgaAqLIEALw_wcB)

(참고2 :https://amaran-th.github.io/React/[Next.js]%20Server%20Component/)

SEO 관련 세미나에서 SSR은 다뤘기 때문에 이번에는 컴포넌트에 대해 다뤄볼 예정이다!
시작 -

Next.js의 Server Component, Client Component

Next.js 13부터 App Router가 등장하면서 pages/ 라우터보다 강력한 기능이 생겼는데 여기서 핵심적인 개념이 바로 Server Client, Client Component이다!

1. 기본 개념 - 서버가 기본, 클라이언트는 예외

우선 Next.js의 기본은 Server Component이다.
즉, 아무 설정을 안 하면 다 서버에서 렌더링 됨!

Server Component란?

  • 서버에서 렌더링
  • 결과물(HTML + React 구조 데이터)을 클라이언트로 보내주는 컴포넌트
  • 브라우저에서는 상태(useState), 이벤트(onClick)가 없음
  • 대신 서버 가까이에서 데이터를 바로 불러올 수 있다!
 // 기본값: Server Component
import { getPost } from '@/lib/data'

export default async function Page() {
  const post = await getPost(1)
  return <h1>{post.title}</h1>
}

=> DB나 API를 호출해도 API 키가 외부로 새지 않고, 불필요한 자바스크립트도 브라우저로 가지 않아 성능이 훨씬 좋음 !

Client Component란?

서버 컴포넌트 안에서는 이벤트 핸들러를 직접 쓸 수 없기 때문에
브라우저에서 동작해야 하는 부분만 따로 분리해서 use client를 선언해준다!

'use client'

import { useState } from 'react'

export default function LikeButton() {
  const [count, setCount] = useState(0)
  return <button onClick={() => setCount(count + 1)}>❤️ {count}</button>
}

=> 브라우저 JS 번들에 포함되고 유저가 클릭하면 실시간으로 상태가 바뀌는 부분이다 !

2. 서버 + 클라이언트 조합

실제 프로젝트에서는 무조건!! 둘을 섞어서 쓸 수밖에 없는 일이 생긴다.

ex. 서버에서 글 데이터 불러오기 + 클라이언트에서 좋아요 버튼만 반응형으로 생성

// app/post/[id]/page.tsx (Server Component)

import LikeButton from '@/app/ui/LikeButton'
import { getPost } from '@/lib/data'

export default async function Page({ params }) {
  const post = await getPost(params.id)
  return (
    <article>
      <h1>{post.title}</h1>
      <p>{post.content}</p>
      <LikeButton likes={post.likes} />
    </article>
  )
}

=> LikeButton은 데이터를 받아 브라우저 쪽에서만 상태를 관리

3. use client 남용 금지

use client를 적는 순간, 그 파일 이하로 import된 모든 코드가 브라우저 번들에 포함된다.

즉,

  • layout.tsxuse client를 넣으면 -> 네비게이션, 푸터, 페이지 전부 클라로 넘어감
  • 이벤트가 필요한 컴포넌트만 따로 분리 -> 성능 good, JS 번들도 훨씬 작아진다.

좋은 예시

// app/layout.tsx (Server)
import Logo from './Logo'
import Search from './Search'

export default function Layout({ children }) {
  return (
    <nav>
      <Logo />
      <Search />
    </nav>
  )
}
// app/Search.tsx (Client)
'use client'
export default function Search() { /* input, useState 등 */ }

-> 이렇게 Search만 Client로 작성하는 것이 좋다. (Logo는 client 사용할 필요가 없으니까!)

나쁜 예시

// layout.tsx
'use client' 

-> 이렇게 되면 전체가 클라이언트로 변해서 번들 사이즈가 어어엄청나게 커지게 된다.

그래서 적절하게 사용하는 방법이 뭔데!

: 데이터를 서버에서 미리 준비해두고, 클라이언트는 필요한 상태만 넘기는 구조로 만들자!

DB -> Server Component -> Client Component

예를 들어 API 키가 필요한 데이터 호출은 서버에서 해야만 안전하다.

// lib/data.ts
import 'server-only'

export async function getSecretData() {
  const res = await fetch('https://api.com', {
    headers: { authorization: process.env.API_KEY },
  })
  return res.json()
}

import 'server-only'를 추가해두면 클라이언트에서 잘못 import 할 경우 빌드 에러로 막아줄 수 있다!

결론

⭐⭐⭐ 모든 걸 클라로 돌리는 게 아니라 정적/데이터는 서버, 상호작용은 클라로 진행하면 된다 ⭐⭐⭐


공부를 하다가 알게 된 건데 원래 리액트는 애플리케이션을 렌더링 하는 주체가 client였다고 한다. 그런데 갑자기?
next13부터는 app 디렉토리가 도입됨에 따라 Server / Client component 개념이 추가되었다고 한다.
그러니까 pages -> app으로 바뀜으로써 (근데 이것도 너무 큰 변화 아닌가? 사실 알못이어서 체감은 잘 못하겠다) 또 공부해야 될 게 생긴 거 아니야 .. ?
next에 대해 이야기(악플)했던 리드님의 세미나가 불현듯 뇌리를 스쳤다.
나 프론트.. 하는 게 맞는 걸까? 이대로 영원히 도태되는 것 아닐까..? 라는 걱정이 앞섰다.
현업에 계신 프론트 개발자분들은 정말 대단하다! 트렌디한 삶을 살아야 해 . .

걱정과 함께 마칩니다.

3개의 댓글

comment-user-thumbnail
2025년 11월 12일

Next.js 문서 공부하고 영주님 블로그까지 보니 학습률이 2배 완성 -⭐
공식 문서는 살짝쿵 이해하기 어려웠는데 영주님 블로그보니 완전 바로 이해됐슴다 !

답글 달기
comment-user-thumbnail
2025년 11월 18일

공식 문서 공부할때도 들었던 생각이지만..컴포넌트를 어떻게 분리할지가 중요할 것 같아요(아닐수도 있구..) 아직도 컴포넌트 분리에 어려움을 격고 있는데 좀 더 연습을 해보면서 어떤 컴포넌트를 사용할지 고민해봐야겠어요!!

답글 달기
comment-user-thumbnail
2025년 11월 24일

요즘 들어 더 절실히 느끼는 컴포넌트 분리의 중요성... 어떻게 컴포넌트를 분리할지에 대한 기준을 잘 세우는 법에 대해 고민하고 공부해야겠어요 잘 정리된 좋은 글!! 잘 읽었습니다 :)

답글 달기