npm create vite-extra@latestssr-react 선택: ssr 환경의 리액트 프로젝트를 만들 목적streaming / non-streamingstreaming: 데이터가 준비되는 대로 실시간·점진적으로 처리/전송. 빠른 반응과 실시간성이 필요할 때 유리non-streaming: 전체 데이터를 모두 준비한 뒤 한 번에 처리/전송, 구현이 쉽고, 단순한 요구에 적합typescript + SWR
프로젝트 설치 후 파일을 확인해보면, SSR을 위한 entry-client.tsx, entry-server.tsx, server.js가 세팅이 되어있다.
import './index.css'
import { StrictMode } from 'react'
import { hydrateRoot } from 'react-dom/client'
import App from './App'
hydrateRoot(
document.getElementById('root') as HTMLElement,
<StrictMode>
<App />
</StrictMode>,
)
위 코드는 SSR(서버 사이드 렌더링)을 지원하는 리액트 프로젝트의 클라이언트 엔트리 파일(entry-client.tsx)에서 자주 볼 수 있는 형태입니다.
hydrateRoot: SSR에서 서버가 미리 렌더링해준 HTML에 리액트가 이벤트 바인딩 등 “수분 공급(hydration)“을 하는 함수입니다.BrowserRouter: 리액트 라우터의 브라우저 기반 라우터(클라이언트 라우팅).App: 리액트 앱의 루트 컴포넌트.
- 왜
hydrateRoot를 쓰는가?
- SSR 환경에서는 서버가<div id="root">...</div>안에 이미 완성된 HTML을 넣어줍니다.
- 클라이언트는 이 HTML을 그대로 활용하고, 이벤트 처리 등 리액트의 기능을 “붙이는” 작업만 합니다. (이 과정을 hydration, 수분 공급이라고 부릅니다.)
- 반면, CSR에서는 HTML이 비어 있고, JS가 모든 UI를 처음부터 그립니다.
- 효과
- 서버가 미리 렌더링한 HTML을 클라이언트가 받아서, 그 위에 리액트가 이벤트 바인딩 및 상태 관리 기능을 붙임(수분 공급).
- 초기 로딩 속도가 빠르고, SEO에도 유리.
import { StaticRouter } from "react-router";
import App from "./App";
import {
renderToPipeableStream,
RenderToPipeableStreamOptions,
} from "react-dom/server";
export function render(_url: string, opts?: RenderToPipeableStreamOptions) {
return renderToPipeableStream(
<StaticRouter location={_url}>
<App />
</StaticRouter>,
opts
);
}
renderToPipeableStream: React 18에서 도입된 SSR용 함수로, React 컴포넌트를 HTML로 렌더링하여 Node.js의 스트림 형태로 반환합니다.StrictMode: 리액트 개발 모드에서 잠재적 문제를 감지하기 위한 래퍼(개발용).App: 리액트 앱의 루트 컴포넌트.RenderToPipeableStreamOptions: 스트리밍 옵션(예: onShellReady, onAllReady 등 콜백 포함).
- 왜
renderToPipeableStream을 쓰는가?
- SSR 환경에서 서버가 리액트 컴포넌트를 HTML로 변환해야 할 때,
React 18부터는renderToPipeableStream을 사용해 스트리밍 SSR을 구현할 수 있습니다.- 이 함수는 Node.js의 스트림에 HTML을 “조각” 단위로 계속 밀어넣어주기 때문에, 클라이언트가 전체 페이지를 기다리지 않고 일부 콘텐츠를 빨리 볼 수 있습니다.
- CSR에서는 이런 기능이 필요 없으므로, 이 함수를 사용하지 않습니다.
- 효과
- 서버가 리액트 컴포넌트를 HTML로 변환해서 클라이언트에 전달합니다.
- 이때 사용하는 함수가
renderToPipeableStream(React 18+) 또는renderToString(React 17 이하)입니다.- 서버에서 HTML을 스트리밍 방식으로 생성하여, 클라이언트가 빠르게 일부 콘텐츠를 볼 수 있습니다.
- 서버 코드에
react-dom/server가 반드시 필요합니다.