리드밋 프로젝트를 하면서 Tanstack Query를 도입해서 사용해보았다.
처음에는 이게 뭔지에 대한 이해 없이, '아~ 이렇게 사용하는거구나' 정도만 알고 구현에만 집중했었는데
친구들과 CS 스터디를 하면서 어떻게, 왜 사용하는건지 제대로 알아보고 넘어갈 수 있었다.
이걸 왜 이렇게 사용하는지, 내장되어있는 기능은 뭐가 있는지,
refetch와 invalidateQueries는 뭐가 다른지 이해하고 넘어갈 수 있는 좋은 기회였다!
그리고 아직 프로젝트에 사용해보지 못한 staleTime, gcTime도.. 적용을 해봐야겠다.
서론이 길었다. 그럼 레지고

프론트엔드에서의 흐름 : fetch → 상태저장 → 로딩/에러 관리 → 데이터 갱신/무효화 → 캐싱
Tanstack Query란?
옛 이름은 React Query이다. 비동기 상태 관리 라이브러리로,
서버 상태를 다루는 데 최적화 되어있다.
Tanstack Query의 특징은?
1. 서버 상태 관리
: API 요청으로 가져오는 데이터(REST, GraphQL 등)는 로컬 상태와 달리 공유되고,
캐싱이 필요하며, 여러 컴포넌트에서 동시에 접근한다. 이를 깔끔하게 관리해주는게 Tanstack Query!
2. 자동 캐싱 & 동기화
동일한 요청은 캐시에 저장해 중복 요청을 막고, 필요할 때 자동으로 최신 데이터로 갱신한다.
캐싱
useQuery를 쓸 때, queryKey를 기준으로 요청 결과를 메모리(cache)에 저장한다.
→ 그래서 동일한 키로 다시 호출하면! 네트워크 요청을 안하고 캐시된 데이터를 바로 보여준다.
예를 들어, 두 컴포넌트에서 같은 데이터를 쓰면? → 첫 번째 요청만 네트워크로 가고, 두 번째는 캐시로 해결됨.
// A 컴포넌트
const { data } = useQuery({ queryKey: ['users'], queryFn: fetchUsers })
// B 컴포넌트
const { data } = useQuery({ queryKey: ['users'], queryFn: fetchUsers })
// 🚫 여기서는 새 API 요청 안 감! 캐시에서 바로 가져옴
동기화
캐시만 있으면 데이터가 오래되었을 수 있기 때문에, TanStack Query는 이걸 자동으로 최신화(refetch)해준다!
|
그래서 기본 동작으로 이들을 다 챙겨주지만, 기본 동작 외에 특별한 정책이 필요하다 하는 경우는 사용자가 직접 해준다.
예를들어,
|
3. 로딩/에러 상태 관리 내장
isLoading, isError, data 같은 상태를 직접 짤 필요 없이 훅에서 바로 제공한다.
4. 리패치(refetch), 무효화(invalidate)
데이터 변경(예: POST, PUT, DELETE)이 일어나면 자동/수동으로 캐시를 무효화해 최신 데이터를 불러온다.
|
5. 백그라운드 업데이트
사용자가 페이지를 보고 있는 동안에도 데이터를 백그라운드에서 조용히 갱신할 수 있다.
| 예를 들어 리드밋의 합주 스케줄 서비스에서 사용자가 시간표 페이지를 켜둔 상태로 있어도, 다른 사람이 스케줄을 바꾸면 내 화면이 자연스럽게 갱신되는 기능을 넣을 수 있다! |
[예시 시나리오]
1. 뉴스 피드
- 사용자가 이미 뉴스 목록을 보고 있음.
- staleTime: 0 (즉시 오래된 데이터로 간주)라면:
- 페이지 들어오자마자 캐시된 데이터를 먼저 보여주고,
- 백그라운드에서 서버에 새 뉴스가 있는지 체크해서 있으면 자동 갱신.
const { data } = useQuery({
queryKey: ['news'],
queryFn: fetchNews,
staleTime: 0, // 항상 오래된 데이터로 간주 → 들어올 때마다 백그라운드 refetch
})
2. 채팅 리스트
- 사용자가 채팅방 목록을 보고 있는데, 다른 브라우저에서 새 메시지가 도착.
- TanStack Query는 포커스 전환 시 자동 refetch 기능이 있어서,
- 사용자가 브라우저 탭을 다른 곳 갔다가 다시 돌아오면
- 백그라운드에서 최신 데이터를 불러와 목록이 새 메시지로 갱신됨.
const { data } = useQuery({
queryKey: ['chats'],
queryFn: fetchChats,
refetchOnWindowFocus: true, // 기본값 true
})
3. 장바구니
- 사용자가 장바구니 페이지를 보고 있음.
- 다른 디바이스에서 같은 계정으로 상품을 추가.
- 사용자가 내 화면을 보고 있어도 → 일정 주기(refetchInterval)마다 백그라운드에서 데이터를 다시 가져와 최신 상태 반영.
const { data } = useQuery({
queryKey: ['cart'],
queryFn: fetchCart,
refetchInterval: 5000, // 5초마다 자동 갱신
})
그러면, Tanstack Query를 사용하는 이유는?
서버 상태 관리의 복잡성을 극복하기 위해 사용한다.
여기서 서버 상태란 서버에서 제공하는 데이터로, 클라이언트에서 직접 수정할 수 없고
네트워크 요청과 같은 비동기 작업을 통해 가져오거나 갱신해야하는 데이터를 의미한다.
Tanstack Query를 사용할 때 발생할 수 있는 단점이나 한계는?
캐싱 관리의 복잡성
강력한 캐싱 기능을 제공하지만, staleTime, gcTime 같은 옵션을 잘못 설정하면
데이터 갱신 타이밍이 적절하지 않아 최신 데이터가 사용자에게 노출되지 않거나 불필요한 요청 발생 가능.
Tanstack-query에서 stale time과 gc time의 차이점?
- stale time : 데이터가 얼마나 오래 ‘신선한 상태’로 유지되는지를 정하는 시간
- 데이터를 처음 가져온 후에 그 데이터를 ‘신선한’상태로 간주하는 시간
- 같은 쿼리에 대한 새로운 네트워크 요청이 일어나지 않고, 캐시 데이터를 그대로 사용하게된다.
- ex. 5분으로 설정하면, 데이터를 가져오고 5분동안은 ‘얘 신선해’ 라고 판단해서 refetch가 트리거되더라도 추가 네트워크 요청 없이 캐시 데이터를 계속 사용.
- 5분이 지나고 refetch가 트리거되면 새로운 요청 보내 데이터 갱신
- 데이터를 처음 가져온 후에 그 데이터를 ‘신선한’상태로 간주하는 시간
- gc time : 해당 쿼리를 사용하는 곳이 없게 된 이후에도 캐시 데이터를 얼마 동안 유지할지를 정하는 시간
- stale time이 지나면 데이터는 ‘오래된’ 상태가 되지만, 여전히 캐시된 데이터는 사용이 가능하다.
- 해당 쿼리가 사용되지 않게 된 시점으로 부터 gc time 으로 설정된 시간이 지나면 캐시에서 데이터가 삭제된다.
학습참고자료
TanStack Query(React Query) 핵심 정리
TanStack Query는 서버로부터 데이터 가져오기, 데이터 캐싱, 캐시 제어 등 데이터를 쉽고 효율적으로 관리할 수 있는 라이브러리로, React Query라는 이름으로 시작했지만, v4부터 Vue나 Svelte 등의 다른
www.heropy.dev
[React] 도대체 Tanstack Query가 뭔데 이렇게 많이 써?
예순 일곱 번째 포스팅
bbjbc.github.io
'✨ FrontEnd > ❄️ React' 카테고리의 다른 글
| [기사] 🚨 React 보안 이슈 - RSC 보안 취약점 발생 (1) | 2025.12.10 |
|---|---|
| react-hook-form과 zod : 폼 상태관리와 유효성 검사 (4) | 2025.05.23 |
| Exoprt default와 그냥 export (Named export) (1) | 2025.04.17 |
| [React] useEffect 제대로 이해해보기 (순수함수와 side Effect) (0) | 2025.03.30 |
| [React] 🚨"props drilling" - 제가 props를 계속 전달 전달하고있는데요... (1) | 2025.03.08 |