- 검색어 추천이 있는 검색창 만들기
- 한국임상정보(https://clinicaltrialskorea.com/) 검색 영역 클론
https://optimize-search-performance.vercel.app/
기술 스택 | 실행 방법 | 의존성 모듈 |
---|---|---|
JavaScript | Repostiory clone : 터미널 창에서 git clone | create-react-app, styled-components |
React.JS | Dependency install : npm install | react-redux, @redux-toolkit |
Redux | Execution : npm start | react-router-dom, axios |
-
로컬 캐싱: LocalStorage에 검색어를 저장하여 동일 검색어의 경우에 활용(expireTime 30분, 파일명: utils/getItemFromLocalStorage.js, utils/setItemToLocalStorage.js)
-
API 호출 최적화: lodash의 debounce를 활용하여 0.5초 지연 입력으로 API호출 과부하 방지(파일명: pages/home.js)
-
키보드 추천어 이동
-
AutoComplete
-
Redux Toolkit으로 전역 상태 관리(Original Redux 보다 덜 구현 환경이 복잡하지 않아서 사용함)
- 본 프로젝트에서 상태는 총 5개이며, 이중에서 props Drilling이 발생하는 상태는 총 3개.
- 배열 인덱스 상태값 - 추천어 배열 리스트에서 현재 특정하고 있는 배열 인덱스의 상태값은 키보드 이동과 AutoComplete을 위해 전역 관리
- 추천어 리스트 상태값 - 추천어 리스트 렌더링 컴포넌트 분리로 전역 관리
- 인풋창 입력값 - props Drilling 발생하지만 Depth가 깊지 않고 setIsLoading, SetShowResult 등의 다른 상태값과 API 호출의 비동기 과정에서 하나의 페이지(Home.js)에서 상태값의 변경이 빈번하여 로컬로 상태 관리
- 검색 영역만을 본다면 상태값을 전역에서 관리할 상태관리 툴의 도입은 크게 필요하지 않는 것으로 판단되나, 추후 기능의 확장성을 고려하여 도입하는 것이 좋다고 여겨짐
- 본 프로젝트에서 상태는 총 5개이며, 이중에서 props Drilling이 발생하는 상태는 총 3개.
-
Atomic component 구조
- API 서버 환경 설정 변화에 따른 데이터 호출 불가 문제
- 정상 작동하던 검색 기능 아래 오류 메세지 발생, CORS 에러
- src 폴더에 setupProxy.js 작성
const express = require('express');
const { createProxyMiddleware } = require('http-proxy-middleware');
const app = express();
module.exports = function(app){
app.use(
createProxyMiddleware('/api', {
target: 'https://api.clinicaltrialskorea.com/',
changeOrigin: true
})
)
};
app.listen(3000);
- axios 요청시에 /api로 호출되는 부분이 proxy 서버로 설정된다고 함
await axios({
method: 'get',
url: `/api/v1/search-conditions/?format=json&name=${item}`,
headers: {
'Content-Type': 'application/json',
},
- 동일한 404 not found 메세지 발생하여 해결되지 않음
- defaultClient.js
import axios from 'axios';
const defaultClient = axios.create({
baseURL:
'https://daground-proxy.herokuapp.com/https://api.clinicaltrialskorea.com',
});
export default defaultClient;
- Home.js axios 호출 영역
import axios from '../utils/defaultClient';
await axios({
method: 'get',
url: `/api/v1/search-conditions/?format=json&name=${item}`,
headers: {
'Content-Type': 'application/json',
},
- 정상 작동
-
맥북 키보드 이동 2회 중복 실행
- 키보드 이동에서 인풋창 --> 추천어 리스트로 이동할 때 인덱스 상태값 증가의 변화가 2번 실행되었음. 프로젝트 자체의 결함이라고 생각하여 원인을 찾으려고 했으나 맥북의 키보드 결함
- 맥북 외의 다른 컴퓨터에서는 정상작동함을 확인하였음. 안정적인 사용을 위해 인덱스 초기값을 -2로 설정하여 맥북의 결함에 대응
-
인풋창의 값이 빈배열일 경우의 상태값 처리와 debounce 적용
- 인풋창의 값을 지울 때에도 debounce를 통한 API호출이 발생하고 호출 결과에 따라 setIsLoading과 setShowResult의 상태값이 변하게 됨
- 인풋창을 Backspace으로 지울 때 debounce의 Delay Time과 비동기 API 호출이 완료되기 전에 인풋창의 값이 빈배열이 될 경우 setIsLoading과 setShowResult의 상태값을 false로 바뀜
- 상태값이 false 바뀐 후에 비동기 API의 호출의 결과로 (즉, 빈배열이 되기 바로 직전의 인풋창의 값으로 API호출이 발생함) setShowResult가 true가 되어서 '검색어 없음' 이 빈배열인 상태에서 활성화된 문제가 있었음
- inputValue 가 빈배열일 경우를 체크해서 setIsLoading과 setShowResult의 상태값을 초기화해주는 명령어를 실행하는 함수를 바꾸어 주어서 해결
- 함수위치 변경 : 처음(debounce가 실행되는 함수) --> 나중(debounce에 의해 실행되는 함수)/ debounce에 의해 실행되는 함수에서 inputValue를 체크해서 비동기의 순차적 실행을 보장