검색어 자동완성 기능을 구현하고 있었다. 그런데 검색어를 입력할 때마다 api요청을 하는 것을 네트워크 탭에서 확인할 수 있었다. 기존의 코드는 아래와 같았다.
// 소스코드의 일부는 생략되었다.
...
const SearchHeaderBox = ({setSearchInput}) => {
...
// 사용자가 검색창에 입력시 동작하는 핸들러 함수
const handleUserInput = (e) => {
// 여기서 데이터 페칭함수를 호출한다.
}
return (
<>
...
<input
title="검색어를 입력해주세요"
placeholder="검색어를 입력해주세요"
...
onChange={handleUserInput}
...
/>
...
</>
)
}
export default SearchHeaderBox
디바운싱은 연이어 호출되는 함수들 중 마지막 함수만 호출하는 것을 말한다. 아래와 같이 재사용이 가능한 커스텀 훅 useDebounce
를 만들어서 디바운스를 구현할 수 있었다. useState
를 사용해서 디바운스된 검색창에 입력한 값을 저장하고, useEffect
를 사용해서 딜레이 시간이 경과했을때의 사용자가 검색창에 입력한 값을 디바운스된 값으로 업데이트 해준다.
// useDebounce.ts
import {useEffect, useState} from 'react';
// 검색시 디바운싱을 위한 커스텀 훅
export default function useDebounce(inputValue: string, delay: number) {
const [debouncedInputValue, setDebounceInputValue] = useState(inputValue);
useEffect(() => {
const timer = setTimeout(() => {
// 0.25초 이후에 인풋 입력값으로 상태업데이트
inputValue && setDebounceInputValue(inputValue);
}, delay);
// setTimeout함수가 반환한 타이머 ID를 제거하지 않으면 이전에 생성된 타이머가 계속되기 때문에 메모리 누수가 발생한다.
return () => clearTimeout(timer);
}, [inputValue, delay]);
return debouncedInputValue;
}
결과적으로 검색어 자동완성 기능에 디바운싱을 적용해서 최대 30건 요청에서 4건으로 줄여서 18.7kb에서 2.5kb로 최대 80% 리소스 세이브할 수 있었다.
디바운싱 적용 전
디바운싱 적용 후
파생되는 문제점이나 더 디벨롭 할 수 있는 부분은 무엇일까?