React Query isFetching 활용: 서버 상태 관리와 로딩 UI UX 최적화
TanStack Query를 마스터하기 위한 첫걸음, 로딩 상태 정복하기
프론트엔드 개발을 하다 보면 가장 고민되는 순간 중 하나가 바로
'데이터를 불러오는 동안 사용자에게 무엇을 보여줄 것인가?'입니다.
사용자는 기다림을 싫어하고, 빈 화면은 이탈률을 높이는 주범이 되곤
합니다.
💡 핵심 문제 제기
혹시 isLoading만 사용하여, 백그라운드에서 데이터를 갱신할
때도 화면 전체를 로딩 스피너로 가리고 계시지는 않나요?
이것은 사용자 경험(UX) 측면에서 좋지 않은 패턴일 수 있습니다.
React Query(TanStack Query)는 이러한 문제를 해결하기 위해
isFetching이라는 강력한 상태를 제공합니다.
오늘 우리는 isLoading과 isFetching의 결정적 차이를
이해하고, 상황에 맞는 세련된 로딩 UI를 구현하는 방법을 알아보겠습니다.
🔍 isLoading vs isFetching: 무엇이 다를까요?
많은 주니어 개발자들이 React Query를 처음 접할 때 가장 혼란스러워하는
부분이 바로 이 두 가지 상태의 차이입니다.
이 둘을 구분하지 못하면 '깜빡임 현상'이나
'불필요한 로딩 화면'을 만들게 됩니다.
1. 명확한 정의 비교
| 상태(State) | 설명 및 특징 |
|---|---|
| isLoading |
캐시 된 데이터가 전혀 없는 상태에서 첫 번째 요청을
보낼 때 true가 됩니다.즉, "보여줄 데이터가 없으니 하드 로딩(스피너 등)이 필수적인 상황"입니다. |
| isFetching |
데이터 유무와 상관없이,
서버로 비동기 요청(QueryFn)이 날아가는 모든 순간에
true가 됩니다.백그라운드 리패칭(Refetching) 시에도 활성화됩니다. |
⚠️ 주의할 점
isLoading이 true라면,
isFetching도 무조건 true입니다.
하지만 isFetching이 true라고 해서
isLoading이 반드시 true인 것은 아닙니다.
🛠️ isFetching으로 똑똑한 UI 만들기
사용자는 이미 화면에 데이터가 나와 있는 상태에서, 최신 정보를 가져온답시고
화면 전체가 하얗게 변하거나 스피너가 도는 것을 원하지 않습니다.
이때 isFetching을 활용하여 부드러운 UX를 제공할 수
있습니다.
✅ 백그라운드 동기화 UI 처리
React Query는 기본적으로 staleTime이 지나면 창 포커싱(Window
Focus) 등의 이벤트 시 자동으로 데이터를 다시 가져옵니다.
이때 기존 데이터를 유지한 채, "업데이트 중..."이라는 작은
인디케이터만 보여주는 것이 좋습니다.
'todos', fetchTodos
);
// 1. 데이터가 아예 없는 초기 로딩
<div>
<h1>할 일 목록</h1>
// 2. 데이터는 있지만 백그라운드 갱신 중일 때
{isFetching && <span>🔄 최신화 중...</span>}
{data.map(todo => <TodoItem key={todo.id} item={todo} />)}
</div>
);
};
-
👍 Good UX: 기존 리스트는 그대로 보여주고, 우측
상단이나 구석에 작은 로딩 아이콘만 노출합니다.
-
👎 Bad UX:
isFetching일 때도isLoading처럼 전체 화면을 스피너로 덮어버려 사용자의 조작을 막습니다.
🚀전역 로딩 상태 관리 (useIsFetching)
개별 컴포넌트가 아닌, 앱 전체에서
"현재 서버와 통신 중임"을 알리고 싶을 때는 어떻게
할까요?
예를 들어, 인스타그램이나 유튜브 상단에 뜨는 얇은 진행 바(Progress Bar)
같은 UI 말이죠.
이때는 useQuery의 반환값이 아닌,
useIsFetching 훅을 사용하면 매우 간단하게
구현할 수 있습니다.
💡 Global Loading Indicator 구현 팁
useIsFetching()은 현재 활성화된 쿼리의 개수를
반환합니다.
이 값이 0보다 크다면 현재 어딘가에서 데이터를 가져오고
있다는 뜻입니다.
const isGlobalFetching = useIsFetching();// isGlobalFetching > 0 ? <TopProgressBar /> : null
✨ 요약 및 마무리
React Query를 사용한다는 것은 단순히 데이터를 가져오는 것을 넘어,
서버 상태(Server State)의 라이프사이클을 관리한다는
의미입니다.
오늘 다룬 isLoading과 isFetching의 차이만 명확히
구분해도, 여러분의 애플리케이션 UX는 훨씬 부드러워질 것입니다.
📝 이것만은 꼭 기억하세요!
- 초기 진입 시 데이터 없음 = isLoading (Skeleton UI 추천)
- 데이터 갱신 및 백그라운드 요청 = isFetching (작은 인디케이터 추천)
- 앱 전체의 통신 상태 확인 = useIsFetching()

댓글 쓰기