728x90
암장예약?하는 사이드 프로젝트에서 next.js 를 사용하고, 카카오맵을 사용한다.
기능으로 현재 위치를 파악하고 위치표시를 하는데 navigator.geolocation을 사용하면 된다는 것을 알게 됨
아래와 같이 Location을 불러오는 함수를 만들고 카카오맵쪽에서 불러오는 방식으로 사용함
/* eslint-disable lines-around-directive */
'use client';
import { useEffect, useState } from 'react';
export default function Location() {
const [location, setLocation] = useState<
{ latitude: number; longitude: number } | string
>('');
const success = (position: GeolocationPosition) => {
setLocation({
latitude: position.coords.latitude,
longitude: position.coords.longitude,
});
};
const handleError = () => {
setLocation({
latitude: 37.483034,
longitude: 126.902435,
});
console.log('Failed to retrieve location');
};
useEffect(() => {
if (navigator.geolocation) {
navigator.geolocation.getCurrentPosition(success, handleError);
} else {
handleError(); // geolocation이 없을때 에러처리
}
}, []);
return location;
}
일단 콘솔에 찍어보고자 console.log(navigator.geolocation)을 입력했지만 navigator is not defined가 떴다.
이상하다 생각해서 console.log(window.navigator.geolocation)를 입력하니 window is not defined가 떴다.
(CSR인 리액트에선 정상적으로 출력이 된다.)
이유?
next는 SSR(Server Side Rendering)으로
서버에서 보여질 HTML을 미리 준비해 클라이언트한테 응답해주는 방식이다.
웹 페이지를 렌더링 할때에 초기에는 window나 document 전역객체는 선언되지 않아 해당 변수를 참조할 수 없기 때문에 벌어진 일이다.
해결
나는 2번을 이용해서 해결했다.
if (typeof window !== 'undefined') 를 사용하거나
export default function weather() {
if (typeof window !== 'undefined') {
console.log(navigator.geolocation);
}
}
//Geolocation {}
useEffect()를 사용하면 해결 가능하다.
import { useEffect } from 'react';
export default function weather() {
useEffect(() => {
console.log(navigator.geolocation);
}, []);