<우아한 타입스크립트 with 리액트> 책을 공부하다가 useRef는 3가지 타입 정의를 가진다는 것을 알게 되었다. 예전에 useRef를 사용했을 때, 인자 타입을 잘못 넣었다가 오류가 발생한 경험이 있다. 그 당시에는 단순히 반환 타입이 달라져서 오류가 생긴 거라고만 알아 두고 넘어갔었다. 이번에 공부하면서 useRef에 대해 자세히 알아보았다.
useRef는 initialvalue로 .current 속성이 초기화된 변경 가능한 참조 객체를 반환한다. 넣어주는 인자(initialValue) 타입에 따라 반환되는 타입이 달라진다. MutableRefObject 또는 RefObject를 반환한다. 반환된 객체는 컴포넌트의 생명주기 동안 유지된다.
3가지 타입 정의
function useRef<T>(initialValue: T): MutableRefObject<T>;
function useRef<T>(initialValue: T | null): RefObject<T>;
function useRef<T = undefined>(): MutableRefObject<T | undefined>;
MutableRefObject의 .current는 값을 변경할 수 있다. 그러나 RefObject는 읽기 전용 값으로 .current 값을 변경할 수 없다.
interface MutableRefObject<T> {
current: T;
}
interface RefObject<T> {
readonly current: T | null;
}
각각의 케이스를 어떤 경우에 사용하는지 예시와 함께 정리했다.
function useRef<T>(initialValue: T): MutableRefObject<T>;
import React, { useRef } from 'react';
function Counter() {
const countRef = useRef(0); // countRef: MutableRefObject<number>
const increment = () => {
countRef.current += 1; // current 값 수정
console.log(`Count: ${countRef.current}`);
};
return <button onClick={increment}>Increment</button>;
}
초기값을 null이 아닌 명확한 값으로 초기화하는 경우 사용한다.
function useRef<T>(initialValue: T | null): RefObject<T>;
import { useRef, useEffect } from 'react';
function FocusInput() {
const inputRef = useRef<HTMLInputElement | null>(null);
useEffect(() => {
if (inputRef.current) {
inputRef.current.focus();
}
}, []);
return <input ref={inputRef} placeholder="Focus me on load" />;
}
초기값으로 null을 설정해야 하는 경우, 주로 DOM 요소와 함께 사용된다.
function useRef<T = undefined>(): MutableRefObject<T | undefined>;
import React, { useRef, useEffect } from 'react';
function Timer() {
const intervalId = useRef<number | undefined>();
useEffect(() => {
intervalId.current = window.setInterval(() => {
console.log('Tick');
}, 1000);
return () => {
if (intervalId.current !== undefined) {
window.clearInterval(intervalId.current);
}
};
}, []);
return <div>Timer running...</div>;
}
초기값 없이 선언해야 하는 경우에 사용된다. 런타임에서 값을 할당하고 참조한다.
이렇게 정리하고 보니, 마지막을 제외하고는 유사하게 사용한 적이 있었다. 각 오버로드 및 타입에 대해 공부했으니 이제 더 잘 사용할 수 있을 것 같다!
참고
'Study > TIL · 오류해결' 카테고리의 다른 글
[TIL] 파일 변환과 확장자 처리 (1) | 2024.12.11 |
---|---|
AWS S3 CORS 문제 해결하기 (+ 브라우저 캐시 문제) (0) | 2024.09.25 |
[TIL] 프론트엔드, 백엔드 도메인이 다를 때 쿠키 설정 (0) | 2024.09.12 |
vite.config.js에서 환경 변수 사용하기 (0) | 2024.09.05 |
[Next.js] 서버 컴포넌트 try-catch에서 redirect가 안 된다 (0) | 2024.08.16 |