React를 배우면서 배웠던 스택으로 CRUD가 작동하는 블로그를 만들었다. 하지만 CSR로 작동하는 블로그의 특징때문에 Reactjs는 사실 좋은 솔루션이 되지는 못했다. 정적인 페이지가 주를 이루는 블로그는 SSR이나 SSG로, 서버에서 렌더링이 이루어져야 더 알맞을 것이다.
이전 블로그는 배웠던 스택들을 구현하는 데 의미를 둔 블로그다. 이 때문에 불필요하게 앱 자체가 동적으로 제작되었다. CSR로 블로그의 글이 렌더링 되어 유저에게 보여지려면 html 파싱과 js 로드를 기다려야 했으며 js로드 이후, 파이어베이스에 있는 데이터를 가지고 와야 하므로 간단한 블로그 앱이더라도 로딩 화면을 피할 수 없었다. 특히 파이어베이스는 최초 데이터 요청에서 상당한 시간이 걸리므로 앱이 굉장히 무겁게 느껴지는 문제가 있었다.
어차피 정적인 콘텐츠를 담고 있는 블로그라면 빌드 시점에 모든 데이터들을 미리 파싱하여 클라이언트의 서버 페이지 요청이 발생했을 때 html 파일만 전달해 준다면 JS로드, data feching시간을 아낄 수 있으므로 TTFB가 극적으로 개선될 수 있다. (홈 페이지 새로고침 시 LCP: 614.8ms-> 106.7ms)
app
┣ posts
┃ ┣ [id]
┃ ┃ ┗ page.tsx
┃ ┗ page.tsx
┣ projects
┃ ┣ [id]
┃ ┃ ┗ page.tsx
┃ ┗ page.tsx
┣ favicon.ico
┣ globals.css
┣ layout.tsx
┣ page.tsx
┗ paper.tsx
블로그 앱은 간단한 구조를 가진다. 리펙터 전과 달리 게시물 작성, 수정, 삭제 기능은 아직 구현되지 않았다. 회원 가입, 댓글 등록, 게시물 관리 등의 기능은 추후에 업데이트 예정이다.
Route (app) Size First Load JS
┌ ○ / 176 B 83.2 kB
├ ○ /favicon.ico 0 B 0 B
├ ○ /posts 2.68 kB 85.7 kB
├ ● /posts/[id] 459 B 337 kB
├ ├ /posts/restful-api
├ ├ /posts/getserversideprops
├ ├ /posts/usememo-usecallback
├ └ [+6 more paths]
├ ○ /projects 5 kB 88 kB
└ ● /projects/[id] 459 B 337 kB
├ /projects/blog
├ /projects/todolist
└ /projects/youtube-clone
+ First Load JS shared by all 83 kB
├ chunks/2443530c-03f4e6061aebc84c.js 50.5 kB
├ chunks/488-6d17156d7c0e6251.js 24.9 kB
├ chunks/920-31aadbf21b65d7f1.js 5.68 kB
├ chunks/main-app-67e757f6b6d0257e.js 217 B
└ chunks/webpack-4a992917812088ee.js 1.73 kB
Route (pages) Size First Load JS
─ ○ /404 183 B 74.9 kB
+ First Load JS shared by all 74.7 kB
├ chunks/framework-43665103d101a22d.js 45.1 kB
├ chunks/main-d413b83cec0718ed.js 27.7 kB
├ chunks/pages/_app-b34b2dcd2ffe424c.js 198 B
└ chunks/webpack-4a992917812088ee.js 1.73 kB
○ (Static) automatically rendered as static HTML (uses no initial props)
● (SSG) automatically generated as static HTML + JSON (uses getStaticProps)
dynamic routes를 이용해서 블로그 글이 SSG로 빌드 시점에 생성된다. 나머지는 Static페이지로 CSR로 렌더링 되는 페이지는 없다.(client component는 존재함)