<

문제해결

[react] useRef 사용 못할 때, createRef

hanseongjun 2025. 7. 4. 02:04
728x90
반응형

문제 상황

함수 안에서 다음과 같이 코드를 작성 - "return { ...task, isEditting: true, ref: useRef<HTMLInputElement>() };".
useRef를 직접 map 내부에서 호출하면 에러가 남


1. 문제의 원인

1-1. React Hook 규칙 위반

  • React의 공식 규칙(React Hooks 규칙, 공식문서)에 따르면,
    Hook(예: useRef, useState, useEffect 등)은 컴포넌트 최상위(혹은 커스텀 Hook)에서만 호출해야 하며,
    조건문, 반복문, 함수 내부 등에서 호출하면 안 됩니다.
  • master의 코드에서
    prevList.map(task => {
      ...
      return { ...task, isEditting: true, ref: useRef<HTMLInputElement>() }; // <-- map 내부에서 Hook 호출
    })
    처럼 map(반복문) 내부에서 useRef를 호출하면 "Invalid hook call" 에러가 발생합니다.

1-2. 공식 문서 근거


2. 해결한 수정사항

2-1. ref를 동적으로 할당하려면 createRef 사용

  • createRef는 Hook이 아니므로 반복문/함수 내부에서 호출 가능합니다.
    (React 공식문서 - createRef)
  • 따라서 아래처럼 수정해야 합니다.

// filepath: App.tsx

import { createRef } from 'react'; // createRef import 추가

// ...existing code...
return { ...task, isEditting: true, ref: createRef<HTMLInputElement>() }; // 수정: useRef → createRef
// ...existing code...

// 주석: createRef는 Hook이 아니므로 map 등 반복문 내부에서 호출해도 React 규칙에 위배되지 않습니다. (공식문서: https://react.dev/reference/react/createRef)


3. 찬성/반대 의견

  • 찬성(createRef 사용):
    • 반복문/함수 내부에서 안전하게 ref 객체를 생성할 수 있습니다.
    • 공식 문서에서도 컴포넌트 외부나 반복문에서 ref가 필요할 때 createRef를 사용하라고 안내합니다.
  • 반대(useRef 반복문 사용):
    • React의 Hook 규칙을 위반하여, "Invalid hook call" 에러가 발생합니다.
    • Hook의 호출 순서가 꼬여서 예측 불가능한 버그가 발생할 수 있습니다.

4. 추가 질문 및 토론 추천 키워드

  1. useRef와 createRef의 차이점과 각각의 사용 시점은 언제가 적절한가?
  2. React Hook 규칙을 위반했을 때 발생하는 실제 버그 사례와 그 영향
  3. 리스트 항목별로 ref를 안전하게 관리하는 패턴(예: Map, 배열, 커스텀 Hook 등)의 장단점

5. 결론

map 등 반복문 내부에서는 반드시 createRef를 사용해야 하며, useRef는 컴포넌트 최상위에서만 호출해야 합니다.

728x90
반응형
LIST