본문으로 건너뛰기

카페인 팀에서 사용하는 지도 라이브러리를 소개합니다.

· 약 9분
가브리엘

지도 api 벤더 선택 이유

국내 서비스 중인 지도 서비스로는 google, naver, kakao가 있습니다.

이 중에서도 google maps api는 css로 지도의 테마를 직접 스타일링할 수 있는 기능이 있어서 선택하게 됐습니다.

google maps api를 사용하기 위해서 별도의 라이브러리 사용이 필수는 아니지만

저희 팀에서 대중적인 라이브러리들과 기본 환경 설정법을 모두 테스트 했을 때, 반드시 사용하고 싶은 라이브러리가 존재하여 비교를 기록으로 남기게 됐습니다.

google maps api 관련 라이브러리

(선택한 라이브러리들은 ✅으로 표시했습니다.)

google maps API

https://github.com/tomchentw/react-google-maps

이 라이브러리는 구글에서 공식으로 제공하는 지도 api로, HTML DOM에 구글 지도를 부착하고, 사용(조작)할 수 있도록 도와줍니다. 이 라이브러리는 vanilla Javascript 기반으로 동작합니다.

@types/google.maps

https://www.npmjs.com/package/@types/google.maps

TypeScript에서 구글 지도를 사용할 때 타입을 제공해주는 역할을 합니다.

@googlemaps/js-api-loader

https://www.npmjs.com/package/@googlemaps/js-api-loader

이 라이브러리는 구글에서 공식으로 제공하는 지도 호출 api로, api key만 넘겨주더라도 구글 지도를 스크립트 형태로 불러와주는 역할을 하는 라이브러리입니다. 별도로 html 조작 없이 불러온 라이브러리에서 구글 지도를 꺼내서 동적으로 사용할 수 있습니다. vanilla Javascript 기반으로 동작하여 어디에서나 사용이 가능합니다.

대중적인 라이브러리 비교

react-google-maps@react-google-maps/api@googlemaps/react-wrapper
링크https://www.npmjs.com/package/react-google-mapshttps://www.npmjs.com/package/@react-google-maps/apihttps://www.npmjs.com/package/@googlemaps/react-wrapper
설명이 라이브러리는 개인이 만든 라이브러리로, google maps API를 react DOM 위에 올려서 사용하게 돕습니다.
구글 지도와 마커를 react component 처럼 사용하여 react스럽게 렌더링 하는 것을 지원합니다.
react 진영에서 가장 대중적으로 사용되는 구글 지도 라이브러리였지만 2018년 이후로 업데이트가 끊겼습니다.
이 라이브러리도 개인이 만든 라이브러리로 앞서 소개한 react-google-maps를 개량하여 만든 라이브러리입니다.
이 라이브러리 역시 react에 지도나 마커 컴포넌트를 호출해서 사용이 가능합니다.
현재 react 진영에서 가장 대중적으로 사용되는 구글 지도 라이브러리 입니다.
이 라이브러리는 구글에서 공식으로 제공하는 react용 라이브러리입니다.
이 라이브러리는 앞서 소개한 js-api-loader를 활용하여 만든 Wrapper 컴포넌트를 제공하는데, 구글 지도를 호출하는 과정에서 수신중, 실패, 성공에 따라 지도를 보여줄 지, 로딩중 컴포넌트를 보여줄 지, 에러 컴포넌트를 보여줄 지 결정하는 기능이 있습니다.
이외에는 기존의 js-api-loader의 기능과 완벽하게 동일합니다. (라이브러리를 열어서 직접 확인해봤습니다.)
선택여부

라이브러리 선택 이유

저희 프로젝트는 실시간 전기자동차 충전소 지도 및 사용 통계 조회 서비스 다보니 지도 위에 띄워줘야 할 마커를 최적화 하는 과정이 굉장히 중요합니다.

  1. 전국 6만여 개의 마커를 전부 보여줄 수 없다.
  2. 현재 디스플레이 영역의 마커만을 호출해야한다.
  3. 그 마커들의 렌더링 과정을 저수준에서 다룰 수 있어야 한다.

이런 원칙을 가지고 있기에 대중적인 라이브러리들(react-google-maps, @react-google-maps/api)은 저희의 선택지에 없었습니다.

따라서 구글 지도는 오로지 vanilla로 제공되는 상태에서 직접 제어하기로 결정하였고, 마커를 관리하는 주체 또한 구글 지도에서 직접 컨트롤을 하려고 합니다.

따라서 구글 지도를 호출하는 작업은 @googlemaps/react-wrapper에 맡기고, 불러온 구글 지도는 vanilla로 통제하기로 했습니다.

지도의 조작, 지도에 마커를 찍는 과정을 모두 공식 문서에 나와있는 방법대로 통제하려고 합니다.

기존의 라이브러리들은 마커나 지도를 컴포넌트화 한 상태이기에 최적화 과정에서 저희가 제어할 수 없는 부분들이 있다고 생각합니다. 따라서 트러블슈팅 과정에서 마커의 호출 시점, 메모리에서 해제하는 시점, 렌더링하는 시점 등의 작업들을 훨씬 더 세밀하게 하려면 google maps api을 있는 그대로 사용할 수 있어야 합니다. 따라서 지도에 관련된 기능은 react DOM 위에서가 아닌 vanilla 환경에서 작업을 할 것입니다.

구글 지도 제어 전략

  1. 구글 지도와 마커는 항상 바닐라 환경(react DOM 바깥)에서 동작하게 한다.
  2. 바닐라 환경에서만 동작하게 하여 리액트 컴포넌트에서의 재 렌더링을 일절 방지한다.
  3. 마커나 지도의 동작 이벤트에 의해 UI를 조작해야하는 경우에는 react DOM 조작을 하도록 한다.
  4. 바닐라 환경인 google maps api와 react DOM 사이의 제어 과정에는 useSyncExternalStore 훅을 이용하여 리액트 UI를 강제로 동기화 시킬 수 있도록 한다.

구글 지도는 바닐라 환경에서, 각종 UI 통제는 리액트에서 통합하여 사용하는 환경을 구상하고 있습니다.

시중에 나와있는 대부분의 라이브러리들을 활용하여 비교하고 테스트한 결과 @googlemaps/react-wrapper를 선택하는 것이 최적화와 생산성, 앱 안정성을 모두 확보할 수 있는 선택이라고 생각했습니다.

현재 카페인 팀에서 사용중인 지도 제어에 관한 방법은 이후에 작성 될 글에서 상세하게 설명하겠습니다.