Ch.12 React 상태 관리 — 살아 움직이는 UI

useEffect — 외부 세계와 연결

useEffect Hook의 개념과 실행 시점을 이해한다의존성 배열의 3가지 패턴을 구별하여 사용할 수 있다useEffect로 API를 호출하고 데이터를 화면에 표시할 수 있다

컴포넌트가 화면에 나타날 때 뭔가를 실행하고 싶다면?

API에서 데이터를 가져오거나, 타이머를 설정하거나, 문서 제목을 바꾸는 등 — 렌더링 외의 작업이 필요할 때

렌더링과 무관한 작업은 어디에 작성할까?

useEffect — 컴포넌트의 생명주기에 맞춰 부수 효과를 실행하는 Hook입니다.


article

핵심 내용

useEffect는 렌더링이 끝난 후 실행되는 '부수 효과'입니다

import { useState, useEffect } from "react";

function DocumentTitle() {
  const [count, setCount] = useState(0);

  // 렌더링 후 문서 제목을 변경
  useEffect(() => {
    document.title = `클릭 ${count}회`;
    console.log("Effect 실행! count:", count);
  });

  return (
    <div>
      <p>{count}회 클릭</p>
      <button onClick={() => setCount(count + 1)}>
        +1
      </button>
    </div>
  );
}

// 렌더링 순서:
// 1. 컴포넌트 함수 실행 (JSX 생성)
// 2. 화면에 표시
// 3. useEffect 실행 (부수 효과)

컴포넌트 마운트: 처음 화면에 나타남 → useEffect 실행

state 변경: 리렌더링 발생 → useEffect 다시 실행

컴포넌트 언마운트: 화면에서 사라짐 → 클린업 함수 실행

부수 효과(Side Effect)란? 컴포넌트의 주 목적(UI 렌더링) 외의 작업들: • API 데이터 가져오기 (fetch) • 타이머 설정 (setInterval) • 문서 제목 변경 (document.title) • 이벤트 리스너 등록/해제 • 로컬 스토리지 읽기/쓰기

의존성 배열로 useEffect의 실행 조건을 제어합니다

useEffect + fetch + useState로 외부 데이터를 가져와 표시합니다

import { useState, useEffect } from "react";

function UserList() {
  const [users, setUsers] = useState([]);      // 데이터
  const [loading, setLoading] = useState(true); // 로딩 상태
  const [error, setError] = useState(null);     // 에러 상태

  useEffect(() => {
    // 마운트 시 API 호출
    fetch("https://api.example.com/users")
      .then(res => {
        if (!res.ok) throw new Error("요청 실패");
        return res.json();
      })
      .then(data => {
        setUsers(data);     // 데이터 저장
        setLoading(false);  // 로딩 완료
      })
      .catch(err => {
        setError(err.message); // 에러 저장
        setLoading(false);
      });
  }, []);  // 빈 배열 → 마운트 시 1회만

  // 로딩 중
  if (loading) return <p>로딩 중...</p>;

  // 에러 발생
  if (error) return <p>에러: {error}</p>;

  // 데이터 표시
  return (
    <ul>
      {users.map(user => (
        <li key={user.id}>{user.name}</li>
      ))}
    </ul>
  );
}

API 호출 패턴 정리 1. 3가지 state 준비: data(데이터), loading(로딩), error(에러) 2. useEffect + 빈 배열: 마운트 시 1회 fetch 호출 3. 로딩/에러 처리: early return으로 상태별 UI 분기 4. 데이터 표시: map()으로 리스트 렌더링 이 패턴은 거의 모든 React 프로젝트에서 사용됩니다!

useEffect의 의존성 배열이 빈 배열 [] 이면 언제 실행되나?

useEffect 안에서 직접 async/await를 사용해도 된다 (useEffect(async () => { ... }))

컴포넌트의 렌더링 이외의 작업(API 호출, 타이머 등)을 ___ 라고 한다

useEffect 마스터!

key

핵심 용어

🔁

의존성 배열 없음

useEffect(() => { ... }) — 매 렌더링마다 실행 (거의 사용 안 함)

1️⃣

빈 배열 []

useEffect(() => { ... }, []) — 마운트 시 1회만 실행 (API 호출)

👀

값 배열 [a, b]

useEffect(() => { ... }, [a, b]) — a 또는 b가 바뀔 때만 실행

edit_note

정리 노트

useEffect — 외부 세계와 연결

useEffect 기본

useEffect(() => {}, [])
컴포넌트 마운트 시 한 번 실행
의존성 배열 []
빈 배열 = 마운트 시만, 배열 생략 = 매 렌더링마다
[값] 의존성
배열 안의 값이 변할 때마다 재실행

활용 패턴

API 호출
fetch()로 외부 데이터를 가져와 state에 저장
cleanup 함수
return () => { ... } — 정리 작업(타이머 해제, 구독 취소)
Side Effect
렌더링과 무관한 외부 작업(API, DOM 직접 조작 등)

useEffect = '렌더링 이후에 이 작업을 해줘'라고 React에게 알려주는 Hook입니다.

image

시각 자료

check_circle

핵심 정리

  • 1useEffect = 렌더링 후 실행되는 부수 효과 처리 Hook
  • 2의존성 배열: 없음(매번), [](1회), [값](값 변경 시)
  • 3API 패턴: data + loading + error state + useEffect fetch

퀴즈와 인터랙션으로 더 깊이 학습하세요

play_circle인터랙티브 레슨 시작