반응형
기존에 사용하던 무한 스크롤 기능은 스크롤이 바닥에 닿는걸 감지해서 무한히 읽어오는 방법으로 구현을 하였습니다.
방법으로는 react-bottom-scroll-listener 라는 라이브러를 이용했습니다.
이 라이브러리는 사용방법이 매우 간단합니다.
useEffect(() => {
firebaseInfinityScrollProjectDataRequest(
setProjects,
lastVisible,
setLastVisible,
);
if (uid) {
firebaseFindMyInterestRequset(uid, setLikedProjects);
}
window.onbeforeunload = () => {
window.scrollTo(0, 0);
};
}, []);
useBottomScrollListener(
useCallback(() => {
firebaseInfinityScrollProjectDataRequest(
setProjects,
lastVisible,
setLastVisible,
);
}, [lastVisible]),
);
useBottomScrollListener 라는 라이브러리에서 제공하는 함수를 이용하면 현재 내가 이용하는 컴포넌트 스크롤이 바닥에 닿는걸 감지해서 안에 있는 로직을 실행 해줍니다.
데이터는 Firebase에서 제공해주는 limit과 startAfter를 사용하여 데이터베이스에 따로 page같은 작업을 하지 않아도 쉽게 구현을 할 수 있습니다. (데이터를 분할로 가져오는 방법은 나중에 자세히 포스팅 하도록 하겠습니다.)
장점으로는 라이브러리에 기본적으로 Lodash가 적용이 되어 있어 쓰로틀 디바운스를 따로 적용 시키지 않아도 최적화 되어 동작을 해서 굉장히 용이하다는 겁니다.
하지만 이 라이브러리에는 치명적인 버그가 있습니다.
미리 스크롤을 밑에까지 내려놓고 해당 컴포넌트로 이동하게 되면 스크롤이 이미 바닥에 닿아있는 거처럼 인식을해 useEffect에서 한번 useBottomScrollListener에서 한번 실행되어 같은 데이터가 2번 들어오게 되는 버그가 있습니다.
이를 위해서 useBottomScrollListener를 lastVisible에 undefined가 아닌 값이 들어 있을때만 실행시켜주면 됩니다.
useBottomScrollListener(
useCallback(() => {
if (lastVisible) {
firebaseInfinityScrollProjectDataRequest(
setProjects,
lastVisible,
setLastVisible,
);
}
}, [lastVisible]),
);
이렇게 해주면 useEffect가 실행되기전에 바닥에 스크롤이 닿아도 실행이 되는 치명적이 오류가 발생하지 않아 예외처리가 굉장히 중요하다는걸 또 한번 느낍니다.
그 외에 무한스크롤을 적용 할 수 있는 방법은 여러가지 있습니다.
그 중 가장 유명한 방법중 하나인 window 객체의 스크롤 값을 비교하는 방법이 제가 방금 적용한 방법입니다.
또 유명한 방법중 하나인 Intersection Observer 라는 방법이 있습니다.
현재 실행하는 컴포넌트가 스크롤의 값을 제대로 감지 할 수 없는 상태라면 이 방법도 굉장히 유용하게 됩니다.
옵저버는 객체 상태변화를 관찰하는 (옵저버)를 등록하여 상태변화가 있을 때마다 각 옵저버에 알리는 패턴입니다.
이 패턴은 Javascript 내장 API인 Observer API 가 있습니다.
두 방법은 각각의 장단점이 있습니다. 하지만 빠르게 프로젝트를 진행해야 하고 안정적인 방법을 찾는다면, Lodash의 디바운스 쓰로틀이 이미 적용이 되어 있는 react-bottom-scroll-listener 을 사용하는 것도 하나의 강점이라고 생각합니다.
반응형
'Frontend' 카테고리의 다른 글
[React] File Resizer 적용기 (0) | 2023.03.19 |
---|---|
[React] CSR이 왜 SEO에 취약한가 CSR vs SSR (0) | 2023.03.18 |
React에서 Toast Editor 적용기 (0) | 2023.02.11 |
[React] useState batching과 동기 비동기에 대하여 (0) | 2023.01.31 |
[React] npm과 npx 의 차이점 (0) | 2022.10.11 |