Data Fetching - 개요
- 서버컴포넌트를 사용하며 서버에서 데이터받아오기
- 병렬적 fetch data를 통해 waterfalls를 예방, 로딩타임 줄이기
- 레이아웃 및 페이지단위에서 중복된 요청 제거하기
- 로딩UI, 스트리밍 및 서스펜스를 이용해서 점진적으로 렌더링하기
The fetch() API - Next.js의 fetch와 native fetch와의 차이점
Next.js에서 쓰이는 fetch API는 브라우저에서 제공하는 그 fetch API가 맞다. 하지만 Next.js에서 쓰일때 조금 더 확장된 기능을 사용가능하다.
- React는 중복된 요청을 제거하기 위해 fetch를 확장적용했다.
- Next.js는 각 요청이 자체적으로 caching 및 revalidating 규칙을 적용할 수 있도록 옵션객체를 확장적용했다.
Fetching Data on the Server - 서버에서 데이터 받아오기
가능만 하다면 Next.js에서는 데이터를 받는 로직을 서버컴포넌트에서 처리하도록 추천하고 있다. 서버컴포넌트는 데이터를 항상 서버에서만 불러오는데, 이러한 방식은 다음과 같은 이점이 있다.
- 백엔드 데이터 리소스(ex:데이터베이스)에 직접 액세스할 수 있다.
- 액세스 토큰 및 API키와 같은 민감한 정보가 클라이언트에 노출되는 것을 방지할 수 있다.
- 데이터를 불러오는 환경과 렌더하는환경이 동일해진다. 이는 클라이언트와 서버간의 통신작업량과 클라이언트의 메인스레드 작업도 감소시킨다.
- 클라이언트서버의 waterfalls가 줄어든다.
- CDN을 이용해 퍼포먼스를 향상시킬 수 있다.
하지만 클라이언트사이드에서 데이터를 받을 수 없는 것은 아니다. 클라이언트 컴포넌트에서는 React Query와 같은 써드파티 라이브러리를 같이 사용하기를 추천한다.
Fetching Data at the Component Level
App router방식에서는 레이아웃, 페이지, 컴포넌트단위 모두에서 데이터를 fetch할 수 있다. 또한 Data fetching은 Streaming and Suspense개념과 같이 사용될 수 있다.
레이아웃의 경우 부모 레이아웃과 하위 컴포넌트 간에 데이터를 전달할 수 없다. 경로에서 동일한 데이터를 여러 번 요청하는 경우에도 데이터가 필요한 레이아웃 내부 즉, 컴포넌트에서 직접 데이터를 가져오는 것이 좋다. 백그라운드에서 React와 Next.js는 동일한 데이터를 두 번 이상 가져오는 것을 방지하기 위해 요청을 캐시하고 중복 제거한다.
Parallel and Sequential Data Fetching
컴포넌트내에서 데이터를 fetching할때에는 두가지 방식에 대해 인지해놓을 필요가 있다.
- 'Parallel' data fetching
- 각각의 데이터의 request들이 동시에 이루어진다. 이는 client-server waterfalls를 미연에 방지하고 로딩타임을 줄이는 이점을 지닌다.
- 'Sequential' data fetching
- 경로의 요청이 서로 종속되어 client-server waterfalls을 생성한다. 하지만 한 데이터의 request가 다른 request의 결과에 의존하거나 리소스를 절약하기 위해 의도적으로 이용할 경우도 있다. (async await와 유사한 개념)
Automatic fetch() Request Deduping
만약 동일한 데이터를 여러 컴포넌트에서 필요로 하는경우 Next.js는 Get(데이터 요청 HTTP)를 임시 캐시에 자동으로 캐시한다. 이 최적화를 통해 rendering pass중 자동적으로 동일한 데이터를 두번 이상 가져오는 것을 방지할 수 있다.
- 서버에서 캐시는 렌더링 프로세스가 완료될 때까지 서버 요청의 수명동안 지속된다.
- 이 최적화는 레이아웃, 페이지, 서버 컴포넌트, generateMetadata, generateStaticParams요청에 적용된다.
- 이 최적화는 static generation중에도 적용된다.
- 클라이언트에서의 캐시는 전체 페이지가 다시 로드되기 전의 세션(여러 클라이언트 측 제렌더링이 포함될 수 있음)동안 지속된다.
POST요청은 자동중복제거가 안된다. fetch를 사용할 수 없는 경우, 요청이 진행되는동안 React의 cache 메서드를 이용해 수동으로 데이터를 저장하면 된다.
Static and Dynamic Data Fetching
데이터를 크게 보자면 둘로 분화될 수 있다.
- Static Data : 블로그의 포스팅글과 같이 그렇게 자주 바뀔필요가 없는 데이터이다.
- Dynamic Data : 쇼핑몰의 장바구니와 같이 자주 변경되거나 사용자에 따라 달라질 수 있는 데이터이다.
- Next.js에서는 static fetches가 기본값이다. 즉, 빌드 타임때 데이터를 가져와서 캐시한 후 동일한 요청에 재사용한다. 하지만 어디까지나 기본값일 뿐 개발자의 역량에 따라 정적 데이터의 cache 및 revalidate는 제어할 수 있다.
- static fetch의 두 가지 이점
- 요청 횟수를 줄여 데이터베이스의 부하를 줄일 수 있다.
- 데이터가 자동으로 캐시되어 캐시된 데이터를 요하는 로직에 대해 로딩 성능이 향상된다.
- 앞서 말했듯, static fetches는 기본값일 뿐 데이터가 사용자에게 다르게 적용되거나 항상 최신 데이터를 요하는 등의 상황에서는 개발자가 입맛대로 dynamic fetches, cache옵션을 사용하지 않고 클라이언트의 요청마다 서버에게 request할 수 있다.
Caching Data
Next.js에서의 Caching은 CDN(e.g Content Delivery Network)방식을 이용한다.
- Next.js 캐시는 전 세계에 배포할 수 있는 영구 HTTP 캐시이다. 플랫폼(예: Vercel)에 따라 여러 지역에 걸쳐 공유될 수 있다.
- Next.js는 fetch() 함수의 옵션 객체를 확장하여 서버의 각 요청이 자체적인 영구 캐싱 동작을 설정할 수 있도록 한다. 컴포넌트내에서 데이터 fetch와 함께 사용하면 데이터가 사용되는 애플리케이션 코드 내에서 캐싱된 데이터가 어디에 사용될지를 구성할 수 있다.
- Next,js는 fetch를 발견하면 cache된 데이터가 있는지를 판별하고 없다면 request후 다음에 사용할 수 있도록 cache한다.
fetch를 사용할 수 없는 경우, 요청이 진행되는동안 React의 cache 메서드를 이용해 수동으로 데이터를 저장하면 된다.
Revalidating Data
revalidate는 저장된 캐시를 지우고 최신 데이터를 다시 가져오는 프로세스이다. 데이터가 변경되어 전체 애플리케이션을 다시 빌드하지 않고도 애플리케이션에 최신 버전이 표시되도록 하려는 경우에 사용한다. (정적 fetch는 빌드타임때만 생성되므로)
Next.js는 두가지 revalidation방식을 제공한다.
- Background : 개발자가 설정한 일정한 시간을 간격으로 자동적 revalidate
- On-demand : 업데이트가 있을때마다 데이터의 revalidate
Streaming and Suspense
Streaming과 Suspense는 UI의 단위를 점진적으로 렌더링하고 스트리밍할 수 있는 React의 새로운 기능이다.
서버 컴포넌트와 중첩된 레이아웃을 사용하면 데이터가 필요하지 않는 페이지의 일부분을 바로 렌더링하고, 데이터를 필요로 하는 페이지의 일부를 데이터가 가져와지는동안 로딩상태로 표시할 수 있다. 즉, 사용ㅎ자는 페이지 전체가 로드될때까지 기다렸다가 페이지와의 상호작용을 시작할 수 있다.
To learn more about Streaming and Suspense, see the Loading UI and Streaming and Suspense pages.
'Next.js(ver.13)' 카테고리의 다른 글
Data Fetching_Caching (0) | 2023.07.14 |
---|---|
Data Fetching_Fetching (0) | 2023.07.10 |
fetch API (0) | 2023.06.27 |
Rendering (0) | 2023.06.27 |