🔥 페이지네이션과 지연 쿼리
TanStack Query에서는 페이지 정보를 쿼리 키에 포함시키는 것만으로도 페이지네이션 데이터를 쉽게 처리할 수 있습니다. 다음과 같이 간단히 구현할 수 있죠:
const result = useQuery({ queryKey: ['projects', page], queryFn: fetchProjects, })
typescript
하지만 이 간단한 예제를 실행해보면 이상한 점을 발견할 수 있습니다. 각 새로운 페이지를 완전히 새로운 쿼리로 취급하기 때문에 UI가 성공 상태와 대기 상태를 오가며 깜빡입니다. 이는 사용자 경험을 해치는 요소입니다.
안타깝게도 많은 도구들이 이런 방식으로 작동하지만, TanStack Query는 다릅니다! 이 문제를 해결하기 위해 TanStack Query는 'placeholderData'라는 멋진 기능을 제공합니다.
placeholderData를 활용한 개선된 페이지네이션 쿼리
페이지 인덱스나 커서를 증가시키는 상황을 생각해봅시다. useQuery를 그대로 사용해도 기술적으로는 문제없이 작동하지만, 각 페이지나 커서에 대해 새로운 쿼리가 생성되고 파괴되면서 UI가 성공 상태와 대기 상태 사이를 오갑니다.
placeholderData에 (previousData) => previousData 함수나 TanStack Query에서 제공하는 keepPreviousData 함수를 설정하면 다음과 같은 이점을 얻을 수 있습니다:
- 쿼리 키가 변경되더라도 새 데이터를 요청하는 동안 마지막으로 성공적으로 가져온 데이터를 사용할 수 있습니다.
- 새 데이터가 도착하면 이전 데이터가 자연스럽게 새 데이터로 교체됩니다.
- isPlaceholderData 값을 통해 현재 쿼리가 제공하는 데이터의 상태를 알 수 있습니다.
다음은 이를 적용한 예제 코드입니다:
import { keepPreviousData, useQuery } from '@tanstack/react-query' import React from 'react' function Todos() { const [page, setPage] = React.useState(0) const fetchProjects = (page = 0) => fetch('/api/projects?page=' + page).then((res) => res.json()) const { isPending, isError, error, data, isFetching, isPlaceholderData } = useQuery({ queryKey: ['projects', page], queryFn: () => fetchProjects(page), placeholderData: keepPreviousData, }) return ( <div> {isPending ? ( <div>로딩 중...</div> ) : isError ? ( <div>오류 발생: {error.message}</div> ) : ( <div> {data.projects.map((project) => ( <p key={project.id}>{project.name}</p> ))} </div> )} <span>현재 페이지: {page + 1}</span> <button onClick={() => setPage((old) => Math.max(old - 1, 0))} disabled={page === 0} > 이전 페이지 </button>{' '} <button onClick={() => { if (!isPlaceholderData && data.hasMore) { setPage((old) => old + 1) } }} // 다음 페이지가 있는지 확인될 때까지 '다음 페이지' 버튼 비활성화 disabled={isPlaceholderData || !data?.hasMore} > 다음 페이지 </button> {isFetching ? <span> 로딩 중...</span> : null}{' '} </div> ) }
typescript
placeholderData를 활용한 무한 쿼리 결과의 지연 처리
placeholderData 옵션은 useInfiniteQuery 훅과도 완벽하게 작동합니다. 이를 통해 무한 쿼리 키가 시간에 따라 변경되더라도 사용자가 계속해서 캐시된 데이터를 볼 수 있도록 할 수 있습니다. 이 방법은 일반적이지는 않지만, 매우 유용한 기능입니다.
이렇게 TanStack Query는 페이지네이션과 무한 스크롤과 같은 복잡한 데이터 로딩 패턴을 쉽게 구현할 수 있도록 도와줍니다. placeholderData를 활용하면 사용자 경험을 크게 개선할 수 있으며, 데이터 로딩 과정에서 발생할 수 있는 UI의 불필요한 깜빡임을 방지할 수 있습니다.