React Query를 사용하려면 다음과 같이 QueryClientProvider로 감싼 후, client prop으로 qeuryClient를 넣어주면 된다.
import {
useQuery,
useMutation,
useQueryClient,
QueryClient,
QueryClientProvider,
} from 'react-query'
import { getTodos, postTodo } from '../my-api'
// Create a client
const queryClient = new QueryClient()
function App() {
return (
// Provide the client to your App
<QueryClientProvider client={queryClient}>
<Todos />
</QueryClientProvider>
)
}
const [coins, setCoins] = useState<CoinInterface[]>([]);
const [loading, setLoading] = useState(true);
useEffect(() => {
(async () => {
const response = await fetch("https://api.coinpaprika.com/v1/coins");
const json = await response.json();
setCoins(json.slice(0, 100));
setLoading(false);
})();
}, []);
위의 코드는 데이터를 불러와서 state에 넣고 로딩을 false로 해주는 것이다.
React Query는 위의 과정을 쉽게 해준다.
우선 fetcher 함수를 만들어야 한다.
export function async fetcher() {
const response = await fetch("-");
const json = await response.json();
return json;
}
그런 후에 useQuery라는 훅을 사용한다.
useQuery는 두가지 인자가 필요하다.
첫번째는 queryKey로 고유식별자이고,
두번째는 fetcher 함수이다.
이 훅은 isLoading이라는 boolean값과 fetcher함수가 끝난 후 가져온 데이터를 반환한다.
isLoading은 fetcher함수가 끝났는지 아닌지를 말해준다.
const {isLoading, data} = useQuery<ICoin[]>("allCoins", fetcher);
react Query를 쓰기전에는 데이터를 가져오는 페이지를 방문할때마다 가져오는데 시간이 걸렸는데 react Query를 쓰면 그런 현상이 사라진다. 데이터를 캐시에 저장해두기때문에 페이지에 들어올때마다 로딩이 필요 없어지기 때문이다.
Devtools를 import 하면 내 캐시에 있는 query를 볼 수 있다.
모든 쿼리는 고유 id를 가지고 있게되는데, 그게 겹칠때가 있을 수 있다. 아래와 같이 하면 된다.
쿼리 키는 문자열처럼 단순할 수도 있고 많은 문자열과 중첩 개체의 배열처럼 복잡할 수도 있다.
const { isLoading: infoLoading, data: infoData } = useQuery<InfoData>(
["info", coinId],
() => fetchCoinInfo(coinId)
);
const { isLoading: tickersLoading, data: tickersData } = useQuery<PriceData>(
["ticker", coinId],
() => fetchCoinTickers(coinId)
);
useQuery의 세번째 인자로는 refetch interval을 줄 수 있다.
const { isLoading: tickersLoading, data: tickersData } = useQuery<PriceData>(
["ticker", coinId],
() => fetchCoinTickers(coinId),
{
refetchInterval: 5000,
}
);