Next.js를 쓰면서 Next.js가 제일 잘하는건 SSR이다 !
라고 … 듣기는 했는데, SSR이란 뭘까? SSR과 같이 이야기되는 CSR은 또 뭘까?
요새는 참 똑똑한분들이 정리를 잘 해놓으시는 것 같다.
위의 글이 너무 잘 정리해놔서 내가 적을 건 없다. 너무 좋으니 한번씩 읽어봐보시길.
그렇다면 나는 눈으로 직접 보면서 둘의 차이점을 알아보자.
일단 두개의 비교를 위해 똑같이 Hello, world를 띄우는 두개의 페이지를 준비했다.
하나는 CSR
방식인 일반 React.js
로 만들고, (나는 vite로 만들었다.)
다른 하나는 SSR
방식인 Next.js
로 만들었다.
일단 두 페이지의 속도차이를 보자.
SSR은 모든 데이터를 매핑해서 가져온다는 특징으로, 초반 로딩이 느리다고했다.
네트워크창을 보면 로드: 610밀리초로 나오는데,
CSR network
CSR은 확실히 로드:125밀로초로 첫 렌더링은 확실히 빠르다.
next.js와 react.js 에 각각 document.body
를 치면 어떤 차이가 있을까 ?
왼쪽: SSR(next.js) / 오른쪽: CSR(react.js)
CSR방식인 react에서는 document.body가 정상적으로 호출되지만,
SSR방식인 next에서는 오류가 발생한다 !
오류를 읽어보면 document is mot defined
가 뜨는데 그 이유는,
사실 document
는 window.document
이다…! (당연한가?)
그래서 CSR인 React에서는 window.document
를 해도 브라우저에서 호출이 된것이기 때문에 호출이 되는 반면,
SSR 방식인 Next에서는 서버에서 매핑이 된다하지않았나 ? 서버에서 만들기때문에 window가 존재하지 않는다…!
그래서 (window.)document.body
가 오류가 뜨는것이다 !
그럼 next에서는 document를 쓰지 못하는걸까 ? document.
이 필요할 땐 어쩌지?
document가 필요한 시점은 dom이 화면에 나왔을때부터이기 때문에 useEffect
로 컴포넌트가 마운트 되고 난 후에 쓰면 호출이 가능하다 !
import { useEffect } from "react";
export default function Home() {
useEffect(() => {
console.log(document.body);
});
return (
<div>
<h1>
SSR <br /> hello, world!
</h1>
</div>
);
}
대충 이런식 ?
Next.js는 SSR로, SEO가 잘된다는 장점이 있다 !
그렇다면 왜? SEO가 잘되는것일까 ?
왼쪽: next.js / 오른쪽: react.js
아까 내가 각각 next.js, react.js 로 hello, world!
를 띄웠다.
그렇다면 각각 두 페이지를 Postman에다가 띄우면 어떤게 나올까?
(페이지 소스보기 Ctrl + U
로도 확인 가능하다.)
Next.js (SSR)
<!DOCTYPE html>
<html lang="en">
<head>
<style data-next-hide-fouc="true">
body {
display: none
}
</style><noscript data-next-hide-fouc="true">
<style>
body {
display: block
}
</style>
</noscript>
<meta charSet="utf-8" />
<meta name="viewport" content="width=device-width" />
<meta name="next-head-count" content="2" /><noscript data-n-css=""></noscript>
<script defer="" nomodule="" src="/_next/static/chunks/polyfills.js?ts=1672325386908"></script>
<script src="/_next/static/chunks/webpack.js?ts=1672325386908" defer=""></script>
<script src="/_next/static/chunks/main.js?ts=1672325386908" defer=""></script>
<script src="/_next/static/chunks/pages/_app.js?ts=1672325386908" defer=""></script>
<script src="/_next/static/chunks/pages/index.js?ts=1672325386908" defer=""></script>
<script src="/_next/static/development/_buildManifest.js?ts=1672325386908" defer=""></script>
<script src="/_next/static/development/_ssgManifest.js?ts=1672325386908" defer=""></script><noscript
id="__next_css__DO_NOT_USE__"></noscript>
</head>
<body>
<div id="__next">
<div>
<h1>SSR <br/> hello, world!</h1>
</div>
</div>
<script src="/_next/static/chunks/react-refresh.js?ts=1672325386908"></script>
<script id="__NEXT_DATA__" type="application/json">
{"props":{"pageProps":{}},"page":"/","query":{},"buildId":"development","nextExport":true,"autoExport":true,"isFallback":false,"scriptLoader":[]}
</script>
</body>
</html>
React.js (CSR)
<!DOCTYPE html>
<html lang="en">
<head>
<script type="module">
import RefreshRuntime from "/@react-refresh"
RefreshRuntime.injectIntoGlobalHook(window)
window.$RefreshReg$ = () => {}
window.$RefreshSig$ = () => (type) => type
window.__vite_plugin_react_preamble_installed__ = true
</script>
<script type="module" src="/@vite/client"></script>
<meta charset="UTF-8" />
<link rel="icon" type="image/svg+xml" href="/vite.svg" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Vite + React + TS</title>
</head>
<body>
<div id="root"></div>
<script type="module" src="/src/main.tsx?t=1672322031531"></script>
</body>
</html>
두개를 보면 각 페이지의 html을 반환하는데,
SSR에는 body안에 hello,world가 뜨는 반면, CSR의 html파일안에는 눈씻고 찾아봐도 hello,world는 찾아볼 수가 없다...
이게 왜 중요하냐 !
이게바로 크롤링이기 때문 …!
검색엔진이 크롤링으로 페이지를 긁어갈 때, 이 html 파일을 읽기 때문이다 !
내가 이 두 페이지를 웹에 올렸다고 했을 때, 사용자가 hello, world 를 검색하면 SSR로 만든 페이지는 뜨겠지만, CSR로 만든 페이지는 뜨지 않을것이다 !
그건 곧 서비스의 수익과도 연결되기 때문에 아주 중요하다 !
마무리
뭔가 CS 지식으로 그냥 SSR이랑 CSR은 이런 차이가 있고, SSR은 SEO가 더 잘되고… 이런걸 아는것보다 직접 실험하고 눈으로 확인하니까 뭔가 더욱 흥미가 생기고 잘 이해가 되는 것 같다 !
앞으로 이런 실험들을 많이 해나가면 좋을 것 같다 !