Notice
Recent Posts
Recent Comments
Link
«   2024/12   »
1 2 3 4 5 6 7
8 9 10 11 12 13 14
15 16 17 18 19 20 21
22 23 24 25 26 27 28
29 30 31
Archives
Today
Total
관리 메뉴

heyday2024 님의 블로그

JavaScript의 History API 본문

프론트엔드 부트캠프

JavaScript의 History API

heyday2024 2024. 11. 11. 20:06

JavaScript의 History API는 클라이언트 단에서의 라우팅을 구현할 때 브라우저의 URL을 조작하며 페이지 이동을 관리하는 데 사용됩니다. 특히 싱글 페이지 애플리케이션(SPA)에서 서버 요청 없이도 URL을 변경하고, 현재 페이지를 새로 고침하지 않으면서 페이지 전환이 이루어지도록 만듭니다.

클라이언트 단 라우팅에서 주요하게 사용하는 History API 메서드는 pushState(), replaceState(), 그리고 popstate 이벤트입니다.

History API 주요 메서드와 이벤트

  1. history.pushState(state, title, url)
    • 설명: 현재 페이지를 새로고침하지 않고도 새로운 URL을 기록해 히스토리 스택에 추가합니다.
    • 사용 용도: 사용자가 다른 페이지로 이동한 것처럼 URL을 업데이트하여 브라우저의 뒤로/앞으로 가기 기능을 사용할 수 있도록 합니다.
  2. history.replaceState(state, title, url)
    • 설명: 현재 히스토리 엔트리를 덮어쓰는 방식으로 URL을 변경합니다. pushState()와 달리 히스토리 스택에 추가하지 않기 때문에 뒤로 가기/앞으로 가기에 영향이 없습니다.
    • 사용 용도: 현재 페이지를 덮어쓰고 싶은 경우나, 초기 페이지 로드 시의 URL을 변경할 때 유용합니다.
  3. popstate 이벤트
    • 설명: pushState()나 replaceState()로 생성된 기록을 통해 브라우저 히스토리에서 앞/뒤로 이동할 때 발생합니다.
    • 사용 용도: 사용자가 뒤로 가기나 앞으로 가기를 누를 때 해당 URL에 맞는 페이지를 렌더링합니다.

클라이언트 단 라우팅 구현 예시

아래 예제는 단일 HTML 파일에서 History API를 이용해 SPA와 비슷한 클라이언트 단 라우팅을 구현하는 예제입니다.

1. 기본 HTML 구조

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>SPA with History API</title>
</head>
<body>
  <nav>
    <a href="/" data-link>Home</a>
    <a href="/about" data-link>About</a>
    <a href="/contact" data-link>Contact</a>
  </nav>
  <div id="app"></div>

  <script src="app.js"></script>
</body>
</html>

2. app.js - 라우팅 구현 코드

// 라우트를 정의
const routes = {
  "/": "Welcome to the Home Page!",
  "/about": "This is the About Page!",
  "/contact": "Reach us at the Contact Page!"
};

// 페이지를 로드하는 함수
function loadPage(path) {
  const appDiv = document.getElementById("app");
  appDiv.textContent = routes[path] || "404 - Page Not Found";
}

// 링크를 클릭할 때 pushState를 이용해 URL 변경하고 페이지를 로드
document.addEventListener("click", (event) => {
  const { target } = event;
  
  if (target.matches("[data-link]")) {
    event.preventDefault();
    const path = target.getAttribute("href");

    history.pushState({}, "", path); // URL을 변경
    loadPage(path); // 페이지를 렌더링
  }
});

// 뒤로가기/앞으로가기 버튼을 누를 때 페이지 로드
window.addEventListener("popstate", () => {
  loadPage(window.location.pathname);
});

// 초기 페이지 로드
loadPage(window.location.pathname);

코드 설명

  1. 라우트 정의: routes 객체는 각 경로(path)와 해당 페이지에 표시할 내용을 매핑합니다. 예를 들어 "/" 경로는 홈 페이지 내용을, "/about" 경로는 소개 페이지 내용을 나타냅니다.
  2. loadPage 함수: 이 함수는 path에 따라 #app 요소에 해당 페이지의 내용을 표시합니다. 존재하지 않는 경로라면 기본적으로 "404 - Page Not Found"를 출력합니다.
  3. pushState로 경로 변경:
    • document.addEventListener("click", ...) 이벤트 리스너는 네비게이션 링크를 클릭할 때 pushState()를 사용하여 URL을 변경하고, loadPage 함수를 호출해 URL에 해당하는 콘텐츠를 표시합니다.
    • 페이지 새로고침 없이 URL이 바뀌며, 히스토리 스택에 새로운 URL이 추가되어 "뒤로 가기" 버튼을 사용할 수 있게 됩니다.
  4. popstate 이벤트:
    • 브라우저의 뒤로 가기/앞으로 가기를 누르면 popstate 이벤트가 발생하고 window.location.pathname에 맞는 페이지를 로드합니다. pushState와 replaceState로 직접 추가한 히스토리만 popstate 이벤트를 발생시키므로 URL을 직접 변경했을 때만 유효합니다.
  5. 초기 페이지 로드:
    • loadPage(window.location.pathname)으로 초기 로드 시 현재 URL 경로에 맞는 콘텐츠를 표시합니다.

동작 과정

  • 처음에 index.html 파일이 로드되면 app.js에서 loadPage 함수가 실행되어 현재 URL에 맞는 내용을 #app에 표시합니다.
  • Home, About, Contact 링크를 클릭하면 pushState()가 호출되어 URL이 변경되고 히스토리 스택에 새로운 엔트리가 추가됩니다. 페이지는 다시 로드되지 않으며, loadPage 함수를 통해 새로운 콘텐츠가 표시됩니다.
  • "뒤로 가기"나 "앞으로 가기" 버튼을 누르면 popstate 이벤트가 트리거되어 loadPage가 호출되고, 적절한 페이지 콘텐츠가 표시됩니다.