TIL - 20250913

juni·2025년 9월 13일

TIL

목록 보기
124/315

0913 React 심화: 전역 상태 관리와 성능 최적화


✅ 1. Context API: Prop Drilling 문제 해결

  • 문제점 (Prop Drilling): 앱의 깊숙한 곳에 있는 컴포넌트에 상태를 전달하기 위해, 중간에 있는 수많은 컴포넌트를 거쳐 Props를 계속해서 전달해야 하는 문제. 코드의 가독성과 유지보수성을 크게 저하시킵니다.

  • 해결책 (Context API): React에 내장된 기능으로, 컴포넌트 트리에 전역적인 데이터 터널을 만들어 Props 전달 없이도 하위 컴포넌트가 데이터에 직접 접근할 수 있게 합니다.

➕ Context API 사용 흐름

  1. createContext: 전역적으로 공유할 데이터의 Context 객체를 생성합니다.
  2. Provider: 생성한 Context 객체에 포함된 Provider 컴포넌트로 앱의 일부를 감쌉니다. value prop을 통해 하위 컴포넌트에 전달할 실제 데이터(상태, 함수 등)를 지정합니다.
  3. useContext: Provider 하위에 있는 어떤 컴포넌트에서든 useContext Hook을 사용하여 value로 전달된 데이터에 직접 접근(소비)합니다.
  • 활용 사례: 장바구니 데이터, 모달의 열림/닫힘 상태, 사용자 인증 정보 등 여러 컴포넌트에서 공유해야 하는 상태를 관리하는 데 매우 유용합니다.

✅ 2. React 렌더링 최적화 기법

  • React는 부모 컴포넌트가 리렌더링되면 기본적으로 모든 자식 컴포넌트도 함께 리렌더링됩니다. 이는 props가 변경되지 않은 자식에게는 불필요한 연산이므로, 성능 저하의 원인이 될 수 있습니다.

➕ 주요 최적화 도구

  1. React.memo:

    • 컴포넌트를 감싸는 고차 컴포넌트(HOC)로, props가 변경되었을 때만 해당 컴포넌트를 리렌더링하도록 만듭니다.
    • React는 이전 props와 현재 props를 얕게(shallowly) 비교하여 변경 여부를 판단합니다.
  2. useCallback:

    • 문제: 컴포넌트가 리렌더링될 때마다 내부에 선언된 함수는 새로운 함수로 다시 생성됩니다. 이 함수를 memo로 감싼 자식에게 prop으로 전달하면, prop이 변경된 것으로 간주되어 memo가 무력화됩니다.
    • 해결: useCallback은 함수 자체를 메모이제이션(memoization)하여, 의존성 배열([])의 값이 변경되지 않는 한 함수를 재생성하지 않고 재사용하게 해주는 Hook입니다.
  3. 컴포넌트 분리:

    • 때로는 복잡한 Hook보다 컴포넌트 구조를 개선하는 것이 더 효과적입니다. 상태가 자주 변경되는 부분과 그렇지 않은 정적인 부분을 별도의 컴포넌트로 분리하면, 리렌더링의 영향을 받는 범위를 최소화할 수 있습니다.

✅ 3. Zustand: 간결하고 강력한 전역 상태 관리

  • Context API는 훌륭한 내장 기능이지만, Provider 설정이 번거롭고 특정 상황에서 불필요한 리렌더링을 유발할 수 있습니다. Zustand는 이러한 단점을 보완하는 간결한 전역 상태 관리 라이브러리입니다.

➕ Zustand의 특징

  1. 최소한의 보일러플레이트: create 함수 하나로 상태(state)와 상태 변경 함수(action)를 포함하는 스토어(Store)를 생성할 수 있습니다.

  2. Provider 불필요: 앱을 <Provider>로 감쌀 필요 없이, 어떤 컴포넌트에서든 스토어를 Hook처럼 호출하여 상태를 구독하고 사용할 수 있습니다.

  3. persist 미들웨어: 단 몇 줄의 코드로 스토어의 상태를 localStorage에 자동으로 저장하고, 새로고침 시에도 상태를 유지하는 영속성을 쉽게 구현할 수 있습니다.

    // store/authStore.js
    import { create } from 'zustand';
    import { persist } from 'zustand/middleware';
    
    const useAuthStore = create(
      persist(
        (set) => ({
          isLoggedIn: false,
          login: () => set({ isLoggedIn: true }),
        }),
        { name: 'auth-storage' } // localStorage에 저장될 키
      )
    );

📌 요약

  • Context APIProp Drilling을 해결하기 위한 React의 내장 전역 상태 관리 솔루션입니다.
  • 불필요한 리렌더링을 방지하여 성능을 최적화하기 위해, React.memo로 컴포넌트를, useCallback으로 함수를 메모이제이션할 수 있습니다.
  • ZustandContext API보다 더 간결하고 직관적인 문법으로 전역 상태 관리를 가능하게 하며, persist 미들웨어를 통해 상태 영속성을 손쉽게 구현할 수 있는 강력한 라이브러리입니다.

0개의 댓글