React + TypeScript에서 컴포넌트 간 데이터 전달은 Props를 통해 이루어져.
이때 타입을 명확히 지정하면 컴포넌트의 사용성과 유지보수가 크게 향상돼.
type WelcomeProps = {
name: string;
age: number;
};
const Welcome = ({ name, age }: WelcomeProps) => {
return (
<div>
<h1>안녕하세요, {name}님!</h1>
<p>당신은 {age}살입니다.</p>
</div>
);
};
// 사용
<Welcome name="박하" age={30} />
✅ Props는 인터페이스나 타입 별칭(type)으로 정의하고 구조 분해를 통해 쉽게 꺼낼 수 있어.
type AvatarProps = {
src?: string;
alt?: string;
};
const Avatar = ({ src, alt }: AvatarProps) => {
return <img src={src ?? '/default.png'} alt={alt ?? '기본 이미지'} />;
};
✅ src?: string은 src가 있을 수도 있고 없을 수도 있다는 의미야. ??는 nullish 병합 연산자로 기본값 처리.
type ButtonProps = {
label: string;
onClick: () => void;
};
const Button = ({ label, onClick }: ButtonProps) => {
return <button onClick={onClick}>{label}</button>;
};
// 사용
<Button label="눌러줘" onClick={() => alert('눌림!')} />
✅ 함수 타입은 () => 반환값 형식으로 작성. 반환값이 없으면 () => void로 명시해야 해.
type ListProps<T> = {
items: T[];
renderItem: (item: T) => React.ReactNode;
};
const List = <T,>({ items, renderItem }: ListProps<T>) => {
return (
<ul>
{items.map((item, idx) => (
<li key={idx}>{renderItem(item)}</li>
))}
</ul>
);
};
// 사용 예시
<List
items={['사과', '바나나', '포도']}
renderItem={(item) => <span>{item}</span>}
/>
✅ 제네릭 <T>는 다양한 타입의 리스트를 유연하게 처리할 수 있게 해줘. <T,>처럼 쉼표는 JSX로 오해되는 걸 방지.