history API

이준구·2024년 6월 27일
0

project

목록 보기
1/2

✨✨ 현재 진행중인 IceCraft 프로젝트의 라우팅 관련 이야기를 해본다.✨✨


🔎 현재 상황

현재: next 14 version의 next/navigation을 사용

처리해야할 경로: main/page.tsx와 동적 라우팅 경로인 room/[id]/page.tsx

방입장: rotuer.push / 방나기: router.replace

수행할 로직: main -> room/[id] 이동 후 뒤로가기 클릭 시 PopState Evenet 실행시켜 조건부 렌더링인 <Loading/> 컴포넌트를 통해 방나가기 로직을 수행

문제: main/page.tsx에서 router.push를 통해 room/[id]/page.tsx 경로로 이동 후 뒤로가기 클릭 시 popState가 정상 작동되지 않는 문제가 발생

이유:
Next.js에서 router.push()를 호출하면 내부적으로 history.pushState()가 실행되지만, Next.js가 SPA(Single Page Application) 구조로써, 브라우저의 페이지를 리로드하지 않고 클라이언트 측에서 URL을 변경하고 컴포넌트를 렌더링하기 때문에 브라우저의 Popstate 이벤트가 이러한 변화를 감지하지 못해 작동되지 않는 문제가 발생한다.

📚📚 popState 정리한 내용

📝 해결방법:

history API를 활용하여 hisyory를 조작

해결방법 순서 1)

  • room/[id]/page.tsx에 접속 시 pushState를 활용하여 현재 roomPage의 history를 추가하였다.
  • 아래의 로직을 통해 뒤로가기 클릭 시 popState가 정상작동되는 걸 볼 수 있다.
  useEffect(() => {
    // history 목록에 추가
    history.pushState(null, "", "")

    const handlePopstate = () => {
      router.replace("/main")
      socket.emit("exitRoom", roomId, userId);
    };

    // 이벤트 리스너 등록
    window.addEventListener("popstate", handlePopstate);

    return () => {
      // 이벤트 리스너 제거
      window.removeEventListener("popstate", handlePopstate);
    };
  }, []);
  • 위 로직을 수행 시 history 목록 및 현재 내 위치


  • 뒤로가기 클릭 시 history 목록 및 현재 내 위치
  • popState 작동 시 방나가기 로직인 router.replace를 통해 Room => Main으로 변경된다.

해결방법 순서 2)

  • 위의 사진을 토대로 뒤로가기 시 현재 내 위치는 history 2번째 Main에 위치
  • 앞으로가기3번째 history인 Room으로 이동되는 구조로써 Room에 다시 접속하는 문제를 해결해야한다.
  • 아래의 로직 해석
    • pushState의 첫번 째 매개변수인 state 상태값을 활용: history.pushState(data, "", "");
    • 뒤로가기 및 앞으로가기 등으로 Room Page를 재접속하였으면, history.state.isAccess값이 존재하여 main Page로 relpace한다.
  useEffect(() => {
    const data = { isAccess: true };
    
    // 재 입장 시 history 상태 값이 존재하므로 현재 history를 Main으로 replace한다.
    if (history.state.isAccess) {
      toast.error("잘못된 접근입니다.");
      router.replace("/main");
      return;
    }
    //첫 입장 시 작동하여 현재 history 상태 값에 "isAccess: true" 저장
    if (!history.state.isAccess) {
      history.pushState(data, "", "");
    }
    
    
    const handlePopstate = (e: PopStateEvent) => {
      router.replace("/main")
      socket.emit("exitRoom", roomId, userId);
    };
    // 이벤트 리스너 등록
    window.addEventListener("popstate", handlePopstate);
    return () => {
      // 이벤트 리스너 제거
      window.removeEventListener("popstate", handlePopstate);
    };
  }, []);
  • 방 입장 시 history 목록 및 현재 내 위치

  • 뒤로가기 시 history 목록 및 현재 내 위치

  • 앞으로 가기 시 history 목록 및 현재 내 위치

한계점: UI에서 깜빡임이 존재 및 그로 인해 UX적으로 실망감을 준다 ㅠㅠ..


👉🏻👉🏻 다음 최종 글 보기

📚📚 참고 문서)

profile
개발 중~~~ 내 자신도 발전 중😂🤣

0개의 댓글

관련 채용 정보