-
Notifications
You must be signed in to change notification settings - Fork 2
๐ useInfiniteQuery๋ฅผ ์ฌ์ฉํ ๊ทธ๋ํ ๋ฌดํ์คํฌ๋กค ๊ตฌํ
๋ถ์ผ | ์์ฑ์ | ์์ฑ์ผ |
---|---|---|
FE | ์กฐ๋ฐฐ๊ฒฝ | 24๋ 12์ 03์ผ |
๋ฌดํ์คํฌ๋กค๋ก ๋ฐ์ดํฐ๋ฅผ ๋ถ๋ฌ์ค๋ฉด ํญ์ ์๋ก์ด ๋ฐ์ดํฐ๋ก ๊ฐฑ์ ๋๋ค.
๊ทธ๋ผ ์ด์ ๊ฐ๋ค์ ์ฐ์งธ..
์ฃผ์ถค์ฃผ์ถค ์๋น์ค์์๋ ๊ทธ๋ํ๋ฅผ ์กฐํํ๋๋ฐ, ๋ฐ์ดํฐ๊ฐ ๊ต์ฅํ ๋ง๊ธฐ ๋๋ฌธ์ 100๊ฐ์ฉ ์๋ผ์ ์๋ต์ ๋ฐ๋๋ค.
๊ทธ๋์ ์ฌ์ฉ์๊ฐ ์ผ์ชฝ์ผ๋ก ์คํฌ๋กคํ์ฌ ์ด์ ๋ฐ์ดํฐ๋ฅผ ํธ์ถํ๋ ค ํ๋ค๋ฉด, ํธ์ถํ๋ ค๋ ๋ฐ์ดํฐ์ ๊ฐ์ฅ ์ต์ ์๊ฐ(lastStartTime
)์ ํจ๊ป ํ๋ผ๋ฏธํฐ๋ก ๋๊ฒจ์ผํ๋ค.
ํธ์ถํ๋ ค๋ ๋ฐ์ดํฐ์ ๊ฐ์ฅ ์ต์ ์๊ฐ์ด๋, ํ์ฌ ๋ณด์ฌ์ง๋ ๊ทธ๋ํ์ ๊ฐ์ฅ ์ค๋๋ ์๊ฐ๊ณผ ๊ฐ๋ค.
๋ฐ๋ผ์ ๊ทธ๋ํ๋ฅผ ์คํฌ๋กคํ๋ค๊ฐ ๊ทธ๋ํ ๊ฐ์๋ฒ์์ ์์์ ์ด ํน์ ์์น๋ณด๋ค ์์์ง๋ฉด, ์ถ๊ฐ ๋ฐ์ดํฐ๋ฅผ ๋ก๋ํ๋ค.
์ด๋, lastStartTime
์ useState๋ก ์ ์ฅํ์ฌ ์ถ๊ฐ ๋ฐ์ดํฐ๋ฅผ ์์ฒญํ๊ณ ์์๋ค.
const fetchGraphData = (logicalRange) => {
// ํน์ ์์น์ ๋ฟ์ผ๋ฉด
if (logicalRange && logicalRange.from < -50 && hasNextPage) {
// ํ์ฌ ๋ฐ์ดํฐ์ ๊ฐ์ฅ ์ค๋๋ ์๊ฐ์ lastStartTime ์ํ์ ์ ์ฅ
setLastStartTime(data?.pages[0].priceDtoList[0].startTime);
// ์๋ก์ด ๋ฐ์ดํฐ ํธ๋ฆฌ๊ฑฐ
fetchNextPage();
}
};
์ฌ๊ธฐ์ ๋ฌธ์ ๋, ์๋ก์ด ๋ฐ์ดํฐ๋ฅผ ๋ฐ์ ๋๋ง๋ค data๊ฐ ๊ฐฑ์ ๋์ด ํญ์ ์๋ก์ด ๋ฐ์ดํฐ๋ง ๊ทธ๋ํ์ ๋ณด์๋ค. ์ฆ ์คํฌ๋กคํ์ฌ ๋ฐ์ดํฐ๋ฅผ ๋ฐ์์ค๋ฉด, ๊ฐ์ด ๋์ ๋๋ ๊ฒ์ด ์๋๋ผ ํญ์ ์คํฌ๋กค๋์ด ์ป์ ๊ฐ์ผ๋ก ๊ฐฑ์ ๋ ๊ฒ์ด๋ค.
๊ทธ๋์ ํญ์ ๋ฐ๋ก ๊ฐ์ ๋์ ํด์ ์ ์ฅํด์ค์ผํ ๊น ์ถ์๋ค.
ํ์ง๋ง ์๋ฒ์์ ๋ฐ์์จ ์๋ต๊ฐ์ ๊ด๋ฆฌํ๊ธฐ ์ํด tanstack query
๋ก ๊ด๋ฆฌํ๊ณ , ๋์ ์ ์ํด useState
๋ก ๊ด๋ฆฌํ๋ค๋ ๊ฒ ๋ฒ๊ฑฐ๋ก์ธ ๊ฒ์ด๋ค.
๊ทธ๋์ ์ด๋ฏธ ๊ตฌํ๋์ด ์์ง ์์์ง ๋ค์ ํ๋ฒ ์ดํด๋ณด๋, useInfiniteQuery
๋ ์๋ต๊ฐ์ ์ด๋ฏธ ๋ฐ์ดํฐ๋ฅผ ๋์ ํ์ฌ ์ ์ฅํ๊ณ ์์๋ค.
useInfiniteQuery
์ ๋ฐํ๊ฐ ์ค data
๋, pages
์ pageParams
๋ฅผ ํฌํจํ๋ค.
- pages: ๋ฌดํ์คํฌ๋กคํ์ฌ ์ป์ด์ง๋ ๋ชจ๋ ๋ฐ์ดํฐ๊ฐ ๋์ ๋์ด ์ ์ฅ
- pageParam: ์์ฒญ์ ํ์ํ ํ์ด์ง ํ๋ผ๋ฏธํฐ
์ฐ๋ฆฌ ํ api์๋ pageParam์ ๋ณ๋๋ก ๋๊ธฐ์ง ์์๊ธฐ ๋๋ฌธ์ ์ด ์ ์ ๊ณ ๋ คํ์ง ์๊ณ ์์๋ ๊ฒ์ด๋ค.
๊ทธ๋ฌ๋ ์๋ต๊ฐ์ ํ์ธํด๋ด๋ ํญ์ ์๋ก์ด ๋ฐ์ดํฐ๋ก ๊ฐฑ์ ๋์ด ์์๋ค. ์ด๋, ์์ฒญ์ ์ต์ ์์ฒด๊ฐ ์๋ชป ์ค์ ๋ ๊ฒ์ด์๋ค.
export const useGetStocksPriceSeries = ({
stockId,
lastStartTime,
timeunit,
}: StockTimeSeriesRequest) => {
return useInfiniteQuery({
queryKey: ['stocksTimeSeries', stockId, lastStartTime, timeunit],
queryFn: () => getStocksPriceSeries({ stockId, lastStartTime, timeunit }),
getNextPageParam: (data) => (data.hasMore ? true : null),
initialPageParam: true,
});
};
getNextPageParam
์ initialPageParam
์ ์ถ๊ฐ๋ก ์ต์
์ผ๋ก ์ค์ ํ๋๋ฐ, ์ด ์๋ฏธ๋ฅผ ์ ๋๋ก ํ์
ํ์ง ์๊ณ ์ฌ์ฉํ๊ณ ์์๋ค.
getNextPageParam
์, ๋ค์ ์์ฒญ์ ํ์ํ ํ๋ผ๋ฏธํฐ๋ฅผ ๋ฐํํ๋ค.
์ฆ ๋ฌดํ์คํฌ๋กค ์์ฒญ ์๋ง๋ค lastStartTime
์ ์ํ๋ฅผ ์๋ก ์ ์ฅํ๋ ๋ก์ง์ getNextPageParam
์์ ์งํํ๋ฉด ๋๋ค.
initalPageParam
์ ๋ง๊ทธ๋๋ ์ด๊ธฐ page ํ๋ผ๋ฏธํฐ ๊ฐ์ด๋ฏ๋ก, lastStartTime
์ ๋๊ฒจ์ผํ๋ค.
์๋๋ ์์ ๋ ์ฝ๋์ด๋ค.
export const useGetStocksPriceSeries = ({
stockId,
lastStartTime,
timeunit,
}: StockTimeSeriesRequest) => {
return useInfiniteQuery({
queryKey: ['stocksTimeSeries', stockId, lastStartTime, timeunit],
// ์์ฒญ์๋ง๋ค ๋๊ธธ pageParam์ ๋ฃ์ด์ฃผ๊ธฐ
queryFn: ({ pageParam }) => getStocksPriceSeries({
stockId,
lastStartTime: pageParam?.lastStartTime ?? lastStartTime,
timeunit
}),
// ๋ค์ ์์ฒญ์ ํ์ํ ํ๋ผ๋ฏธํฐ๋, hasMore๊ฐ true์ผ ๋ ์ค์ ํด์ฃผ๊ธฐ. ์ด์ ์ setState ๊ณผ์ ์ด ํ์ ์์ด์ง๋ค!
getNextPageParam: (lastPage) =>
lastPage.hasMore
? {
lastStartTime: lastPage.priceDtoList[0].startTime
}
: undefined,
initialPageParam: { lastStartTime },
});
};
๊ทธ ๊ฒฐ๊ณผ, ๊ฐฑ์ ๋ ๋ฐ์ดํฐ๊ฐ pages์ ์ฐจ๊ณก์ฐจ๊ณก ๋ด๊ธด๋ค!
์ฌ์ค์ ์ด์ ๋ฐ์ดํฐ๋ฅผ ๋ถ๋ฌ์ค๋ ๊ฒ์ด๋ getNextPageParam
๋์ ์๋ getPreviousPageParam
, hasNextPage
๋์ ์ hasPreviousPage
๋ฅผ ์ฐ๋ ๊ฒ ์๋ฏธ์ ์ ์ ํ๋ค.
ํ์ง๋ง getPreviousPageParam๋ฅผ ์ฌ์ฉํ๋ คํ๋ฉด, ์ด ํธ์ถ๊ณผ ์ผ์นํ๋ ์ค๋ฒ๋ก๋๊ฐ ์์ต๋๋ค.
๋ผ๊ณ ์์ธ ๋ชจ๋ฅผ ์๋ฌ๊ฐ ๋ฐ์ํ๋ค.
๋ํ getPreviousPageParam์ ์ฝ๋ฐฑ์ ํ๋ผ๋ฏธํฐ์ธ firstPage, allPages, firstPageParam, allPageParams๋ก hasMore๋ฅผ ๋ถ๋ฌ์ฌ ์ ์์ด ์์ ์ฝ๋์ ๊ฐ์ ๋ก์ง์ ์งค ์ ์์๋ค.
๋ฐ๋ผ์ getNextPageParam
์ ์ด์ฉํด ์ด์ ๋ฐ์ดํฐ๋ฅผ ๋ถ๋ฌ์ค๊ณ , select ์ต์
์ reverse()
๋ฅผ ํตํด ์ญ์์ผ๋ก ์ ์ฅํ์ฌ ๊ทธ๋ํ๋ฅผ ๊ทธ๋ฆฌ๊ณ ์๋ค.
select: (data) => ({
pages: [...data.pages].reverse(),
pageParams: [...data.pageParams].reverse(),
}),
- ๐ฉ FE ๊ธฐ์ ์ ํ์ด์
- โจ ์ฐจํธ์ ๋ฐ์ํ ๊ตฌํ๊ณผ useRef ํ์ ๋ฌธ์
- ๐ฃ ๋ถ๋ชจ ์์์ ์ํ์ ๋ฐ๋ผ ์์ ์์๋ ์คํ์ผ ๋ณํ ๋ถ์ฌํ๊ธฐ
- ๐ zod ๋์ ํ๊ธฐ
- ๐ useInfiniteQuery๋ฅผ ์ฌ์ฉํ ๊ทธ๋ํ ๋ฌดํ์คํฌ๋กค ๊ตฌํ
- ๐ซ ์ฌ์ฉ์์ ์์ ๋ณํ ์๋ ๊ทธ๋ํ ์คํฌ๋กค ๊ตฌํํ๊ธฐ
- ๐งช ์๋ง์ ๊ทธ๋ํ ๋ฐ์ดํฐ ์์ฒญ์ ์ด๋ป๊ฒ ์ค์ผ๊น
- ๐ ๋คํฌ๋ชจ๋์์ ์๋ก๊ณ ์นจ ์ ๋ผ์ดํธ๋ชจ๋๊ฐ ์ ๊น ๋ณด์ด๋ ๋ฌธ์
- ๐ ์น์์ผ์ ์ฑํ ๋ฐ์ดํฐ์ REST API์ ์ฑํ ๋ฐ์ดํฐ๋ฅผ ํจ๊ป ๊ด๋ฆฌํ๊ธฐ
- ๐ก BE ๊ธฐ์ ์ ํ ์ด์
- โ๏ธ Node WebSocket ํ๊ณ ๋ค๊ธฐ
- โ๏ธ TypeORM Datasource mock ๋ง๋ค๊ธฐ
- โ๏ธ oauth ID range ๋ฌธ์
- ๐ custom pipe์์ Nan์ด ๋ฐ์์ง๋ ๋ฌธ์
- ๐ช nest Websocket์ ์ธ์ ์ด ์๋๋ค๊ณ ?
- ๐ด nginx websocket ์ฐ๊ฒฐ ์ ๋ฌธ์ ๋ฐ์
- ๐ WebPush ๊ตฌํ
- ๐ง ์ฐ์ ์์ ํ๋ก ์์ฒญ ์ ์ดํ๊ธฐ
- ๐ websocket์ด ๋ฆ๊ฒ ํ ๋น๋์ด ๋ฐ์๋๋ ๋ฌธ์
- ๐ฅณ typeorm์ ์ด์ฉํ FCM ์๋ฆผ ์๋น์ค
- ๐ฆ ๋ค์ค ์ ์ ๋์์ฑ ์ ์ด โ ์ฑ๊ธํค, ๋ฎคํ ์ค
- ๐ ๊ทธ๋ํ ๋ฐ์ดํฐ๋ฅผ ์ค์๊ฐ์ผ๋ก ์ ๊ณตํ๊ธฐ์ํ ์ ๋ต
- ๐ ๏ธ ์ธํ๋ผ ๊ธฐ์ ์คํ ์ ํ ์ด์
- ๐ Ncloud ์ค์ ๊ณผ์
- ๐ ORM ๊ธฐ์ ์คํ ๋น๊ต
- ๐ค RabbitMQ๋ก ๋ถ์ฐ ์๋ฒ์๊ฒ ๋ฉ์์ง๋ฅผ ๋ถ๋ฐฐํ๊ธฐ
- ๐ข private DB ์๋ฒ์ ์ ์ํ์ง ๋ชปํ๋ ํ์
- ๐ 1์ฃผ์ฐจ ๋ฐํ
- ๐ 2์ฃผ์ฐจ ๋ฐํ
- ๐ 3์ฃผ์ฐจ ๋ฐํ
- ๐ 4์ฃผ์ฐจ ๋ฐํ
- ๐ 5์ฃผ์ฐจ ๋ฐํ
- ๐ ์ต์ข ๋ฐํ