๐ react-query๋ฅผ ์ฌ์ฉํด์ผ ํ๋ ์ด์
๋ฆฌ์กํธ์์ ์ํ ๊ด๋ฆฌ๋ฅผ ์ํ ๋ผ์ด๋ธ๋ฌ๋ฆฌ๋ ๋ฌด์ํ ๋ง์ต๋๋ค.
๋ํ์ ์ผ๋ก redux
, recoil
๊ฐ์ ๋ผ์ด๋ธ๋ฌ๋ฆฌ๊ฐ ์๋๋ฐ,
๋๋ถ๋ถ ์ด๋ฌํ ์ํ ๊ด๋ฆฌ ๋ผ์ด๋ธ๋ฌ๋ฆฌ๋ฅผ ์ฌ์ฉํ๋ฉฐ
ํด๋ผ์ด์ธํธ ์ํ์ ์๋ฒ ์ํ๋ฅผ ํจ๊ป ๋ด์๋๊ณ ์๋ ๊ฒฝ์ฐ๊ฐ ๋๋ถ๋ถ์ด๊ณ , ๋ ๊ทธ๋ด ์ ๋ฐ์ ์์์ต๋๋ค.
react-query๋ฅผ ์ฌ์ฉํด ์๋ฒ ์ํ๋ฅผ ๊ด๋ฆฌํ๋ค๋ฉด ํด๋ผ์ด์ธํธ ์ํ๋ฅผ ๋ถ๋ฆฌํ์ฌ ๊ด๋ฆฌํ ์ ์๊ธฐ ๋๋ฌธ์
์ง๊ด์ ์ด๊ณ ํจ์จ์ ์ธ ๊ด๋ฆฌ๊ฐ ๊ฐ๋ฅํด์ง๋๋ค.
์ด ์ธ์๋ react-query์์ ์ง์ํ๋ ๋ค์ํ ์ต์
๋ค์ ์ฌ์ฉํด
์บ์ฑ, ์๋ฌ์ฒ๋ฆฌ, suspense, refresh, data fetching ์กฐ๊ฑด ์ค์ ๋ฑ๋ฑ
๊ธฐ์กด์ ๋ถํธํ๊ฒ ๋๊ผ๋ ๋ถ๋ถ๋ค์ ์ ์ธ์ ์ด๊ณ ๊ฐํธํ๊ฒ ์ด์ฉํ ์ ์๋๋ก ๋์์ค๋๋ค.
๊ทธ๋ผ react-query๋ฅผ ์ฌ์ฉํ ๋ ๋๋ฆด ์ ์๋ ์ด์ ๋ค์ ์์๋ณด๊ฒ ์ต๋๋ค.
์๋กญ๊ฒ ์ ๋ฐ์ดํธ ๋ react-query v5 ๋ฒ์ ์ ๊ดํ ๋ด์ฉ๋ค์ ๋น ๋ฅด๊ฒ ์์๋ณด๊ณ ์ถ์ผ๋ฉด ๋ค์ ๊ธ์ ์ฐธ๊ณ ํด์ฃผ์ธ์!
react-query v5 ์ฃผ์ ๋ณ๊ฒฝ์ ์์๋ณด๊ธฐ feat. Suspense, ErrorBoundary
๐ Data Fetching ๋ก์ง ๋จ์ํ
๊ธฐ์กด์ ์๋ฒ์์ ๋ฐ์ดํฐ๋ฅผ ๊ฐ์ ธ์ค๊ธฐ ์ํด์๋ ๋ค์๊ณผ ๊ฐ์ ์ ์ฐจ๊ฐ ํ์ํ์ต๋๋ค.
- Fetching ์ฝ๋ ์์ฑ
- ๋ฐ์ดํฐ๋ฅผ ๋ด์ ๋ ์ํ ์์ฑ
- useEffect๋ฅผ ์ด์ฉํด ์ปดํฌ๋ํธ Mount์ ๋ฐ์ดํฐ๋ฅผ Fetching ํ ๋ค ์ํ์ ์ ์ฅ
import { useEffect, useState } from "react";
const getServerData = async () => {
const data = await fetch(
"https://jsonplaceholder.typicode.com/posts"
).then((response) => response.json());
return data;
};
export default function App() {
const [state, setState] = useState<any[]>([]);
useEffect(() => {
getServerData()
.then((dataList) => setState(dataList))
.catch((e) => setState([]));
}, []);
return <div>{JSON.stringify(state)}</div>;
}
์์ ๊ฐ์ ์ฝ๋๋ฅผ react-query๋ฅผ ์ฌ์ฉํ๋ค๋ฉด ๋ค์๊ณผ ๊ฐ์ด ๋ฐ๊ฟ ์ ์์ต๋๋ค.
import { useQuery } from "@tanstack/react-query";
const getServerData = async () => {
const data = await fetch(
"https://jsonplaceholder.typicode.com/posts"
).then((response) => response.json());
return data;
};
export default function App() {
const { data } = useQuery(["data"], getServerData);
return <div>{JSON.stringify(data)}</div>;
}
์๋ฒ ๋ฐ์ดํฐ๋ฅผ ๋ด์ ์ํ๋ฅผ ๋ง๋ค๊ณ useEffect
๋ก ์ํ์ ๋ฐ์ดํฐ๋ฅผ ๋ด๋ ๋ชจ๋ ๊ณผ์ ์useQuery
๋จ ํ์ค๋ก ์ฒ๋ฆฌํ ์ ์์ต๋๋ค.
์ด๋ก ์ธํด ๋ฐ์ํ๋ ์ฅ์ ์ ๋ค์๊ณผ ๊ฐ์ต๋๋ค.
๐ ์ฝ๋ ์ ๊ฐ์
์ผ๋ฐ์ ์ธ ์๋ฒ ๋ฐ์ดํฐ๋ฅผ ๋ฐ์์ค๋ ๊ณผ์ ์ ์ฝ๋๊ฐ ๊ทธ๋๋ ์ผ๋ง ์๋๊ฒ ๋ค๊ณ ์๊ฐํ๊ฒ ์ง๋ง
๋ฐ์ ์ฌ ์๋ฒ ๋ฐ์ดํฐ์ ๋น๋กํด์ ์ถ๊ฐ๋๋ ์ํ์ Side Effect
๋ฅผ ์๊ฐํ๋ฉด ๊ต์ฅํ ๊ฐ๋ ฅํ ์ฅ์ ์
๋๋ค.
๐ Side Effect ์ ๊ฑฐ
ํนํ๋ ์ํ๋ง๋ค ์์ฑํด์ฃผ์ด์ผ ํ๋ useEffect
๋ฅผ ๊ฑท์ด๋ผ ์ ์๋ค๋ ๊ฒ์
์๋ฒ ๋ฐ์ดํฐ๋ก ๋ฐ์ํ๋ ์ฅํฉํ Side Effect
๋ก ์ธํด ํ๋ฆ ํ์
์ ์ด๋ ต๊ฒ ๋ง๋ค์๋ ๋ฌธ์ ๋ฅผ ํด๊ฒฐํฉ๋๋ค.
๐ Data Fetching ๋ฐฉ์ ๊ท๊ฒฉํ
์๋ฒ์์ ๋ฐ์ดํฐ๋ฅผ ๋ถ๋ฌ์ค๋ ๋ฐฉ๋ฒ์ ๋ช
ํํ ์ ๋ต์ ์๊ธฐ ๋๋ฌธ์
๊ฐ๋ฐ์๋ค๋ง๋ค ๊ฐ๊ฐ์ธ์ ๋ฐฉ์๋๋ก ๋ฐ์ดํฐ๋ฅผ ๋ถ๋ฌ์ค๋ ์ฝ๋๋ฅผ ์์ฑํฉ๋๋ค.
๊ทธ๋ ๊ธฐ ๋๋ฌธ์ ์ ๊ฐ๊ฐ์ผ๋ก useEffect
๋ฅผ ์ฌ์ฉํ๋ค๋ณด๋
์์ ์ด ์ง ์ฝ๋๋ผ๋ ์ ์ฒด์ ์ธ ํ๋ฆ์ ํ์
ํ๋ ๊ฒ์ด ์ฝ์ง ์์๊ณ ,
๋ค๋ฅธ ์ฌ๋์ด ์์ฑํ ์ฝ๋๋ฅผ ๋ณด๋ฉฐ ์์ ํ๋ ์ผ์ ๋์ฑ๋ ์ด๋ ค์ ์ต๋๋ค.
๊ทธ๋ฌ๋ react-query๊ฐ ๋ด์ฅ๋ ๊ธฐ๋ฅ์ผ๋ก ๊ด๋ จ ๋ก์ง๋ค์ ์ ๋ถ ์ฒ๋ฆฌํด์ฃผ๋
์ง์ํ๋ ํ
์ ์ด์ฉํด ๋ชจ๋๊ฐ ํ์ผํ ๋ ๋ฐฉ์์ผ๋ก ์ฝ๋๋ฅผ ์์ฑํ ์ ์์ต๋๋ค.
๐ ๋๊ธฐ์ ์คํ
์ด๋ ํ API๋ฅผ ํธ์ถํ๊ธฐ ์ํด ๋ค๋ฅธ API์ ๊ฐ์ ํ๋ผ๋ฏธํฐ๋ก ๋ฃ์ด์ค์ผ๋ ๋๊ฐ ์์ต๋๋ค.
๊ทธ๋ฌ๊ธฐ ์ํด์ ๋๊ธฐ์ ์ผ๋ก API๋ฅผ ํธ์ถํด์ฃผ์ด์ผ ํฉ๋๋ค.
const [state1, setState1] = useState();
const [state2, setState2] = useState();
useEffect(()=>{
getServerData().then((dataList)=>{
setState1(dataList[0]);
})
},[]);
// state1์ ๋ฐ์ดํฐ๋ฅผ ํ๋ผ๋ฏธํฐ๋ก ๋ฃ์ด ํธ์ถํ๋ API
useEffect(()=>{
if(state1){
getAfterData(state1).then((dataList)=>{
setState2(dataList);
})
}
},[state1]);
๊ฐ๋ตํ๊ฒ ํํํด๋ดค๋๋ฐ๋ ์ฝ๋์์ด ๋ง์ต๋๋ค.
๊ฒ๋ค๊ฐ API ํธ์ถ์ ์ํ ์กฐ๊ฑด๋ ์ถ๊ฐ๋์ด ๋๊ธฐ์ ์ผ๋ก ๊ด๋ฆฌ๊ฐ ํ์ํ๊ณ ,
useEffect์ ์์๊ฐ ๋ค๋ฅธ ์ฝ๋๋ค๊ณผ ์์ธ๋ค๋ฉด
์ด๋ค ๋ฐ์ดํฐ๊ฐ ์ธ์ , ์ด๋ป๊ฒ ํธ์ถ ๋๋์ง ํ๋ฆ๊ณผ ์์ ์ ํ์
ํ๊ธฐ ์ด๋ ค์์ง๋๋ค.
const { data: data1 } = useQuery(["data1"], getServerData);
const { data: data2 } = useQuery(["data2", data1], getServerData, {
enabled: !!data1
});
react-query ์ต์
์ค enabled
์ ์กฐ๊ฑด์ด ์ถฉ์กฑ๋ ๋๋ง API๋ฅผ ํธ์ถํ๊ฒ ๋์ด
์์ ๊ฐ์ด ์ ๋ง ๊ฐ๋จํ๊ฒ API๋ฅผ ๋๊ธฐ์ ์ผ๋ก ํธ์ถํ ์ ์์ต๋๋ค.
๐ ์บ์ฑ
ํ ์ ํธ์ถํ ๋ ๋ค์๊ณผ ๊ฐ์ ์ต์ ์ ์ฌ์ฉํ๋ฉด ๋ฆฌ์กํธ ์ฟผ๋ฆฌ์ ์บ์ฑ ๊ธฐ๋ฅ์ ์ด์ฉํ ์ ์์ต๋๋ค.
staletime
ํธ์ถํ ๋ฐ์ดํฐ๋ ๋ฆฌ์กํธ ์ฟผ๋ฆฌ ์์ฒด์ ์ผ๋ก ์ ์ฅ์ ํด๋ก๋๋ค.
staletime์ ์ด ์บ์๋ฐ์ดํฐ์ ์ ํต๊ธฐํ์ ์ ํด์ฃผ๋ ์ต์ ์ ๋๋ค.
default๋ 0์ผ๋ก, ๋ณ๋ค๋ฅธ ์ต์ ์ธํ ์ ํด์ฃผ์ง ์๋๋ค๋ฉด
๋ฐ์ดํฐ๊ฐ staleํ๋ค๊ณ ํ๋จํ์ฌ ์บ์ฑ ๊ธฐ๋ฅ์ ์ด์ฉํ ์ ์์ต๋๋ค.cachetime
cashetime์ ์ ์ฅํ ๋ฐ์ดํฐ๋ฅผ ์ผ๋ง๋ ์ ์งํ ์ง ์ ํด์ฃผ๋ ์ต์ ์ ๋๋ค.
default๋ 5๋ถ์ ๋๋ค.
const { data } = useQuery(['data', getServerData,{
staletime: 10 * 60 * 1000;
cashetime: 10 * 60 * 1000;
})
์์ ๊ฐ์ด ์ต์
์ ์ง์ ํด์ฃผ๋ฉด ๋ณ๋ค๋ฅธ refresh๊ฐ ์์ ๋
10๋ถ ๋ด ์ฌํธ์ถ์ API๋ฅผ ํธ์ถํ์ง ์๊ณ ์บ์ฑ๋ ๋ฐ์ดํฐ๋ฅผ ์ ๊ณตํด์ค๋๋ค.
๐ Suspense ์ฌ์ฉ
Suspense์ ๊ด๋ จ๋ ์์ธํ ์ด์ผ๊ธฐ๋ ์ ์ ์์ฑํด๋๋ ๊ธ์ ์ฐธ๊ณ ํด์ฃผ์ธ์.
2023.03.23 - [Web/React] - [React] Suspense์ ์ฌ์ฉํด ์ ์ธ์ ์ผ๋ก ๋ก๋ฉ ํ๋ฉด ๊ตฌํํ๊ธฐ
๐ ๋ง๋ฌด๋ฆฌ
์ ๊ฐ ์๊ฐํ๊ธฐ์ ๊ฐ์ฅ ์ฌ์ฉํด๋ณด๊ณ ์ถ์ ๊ธฐ๋ฅ๋ค ์์ฃผ๋ก ์ค๋ช
ํด๋ดค์ง๋ง
์ด ์ธ์๋ ์๋ฌ์ฒ๋ฆฌ์ ๋ค์ํ ๋ฐ์ดํฐ refresh ๋ฐฉ๋ฒ, data update ๋ฑ๋ฑ ๋ ๋ง์ ์ฅ์ ์ด ์กด์ฌํ๊ธฐ ๋๋ฌธ์
๋ค์ ํ๋ก์ ํธ์์ ๋ฐ๋์ ์ฌ์ฉํด๋ณด๊ณ ์ถ๋ค๋ ์๊ฐ์ ํด๋ด
๋๋ค.
๋๊ธ