본문 바로가기
이론/Frontend

리액트에서 기본 컴포넌트를 만들때

by 유세지 2022. 12. 22.

 

 

이번에 사이드 프로젝트를 하며 맞닥뜨렸던 문제인데, 잊기전에 간단히 정리해두려 합니다.

 

문제 상황

 

프로젝트를 처음 시작하면, 디자인을 적용하기 위해 자주 쓰는 기본 HTML 요소들을 커스텀 컴포넌트로 만들게 됩니다. 예를 들면 <Button> 태그나 <Input> 태그등이 있습니다. 보통 아래처럼 다양한 props들을 받을 수 있도록 여러가지 인자를 선언해두고 사용합니다.

 

 

export interface InputProps {
  isValid?: boolean;
  hasUnderline?: boolean;
}

const Input = ({
  isValid = true,
  hasUnderline = false,
}: InputProps) => {
  return <S.Input isValid={isValid} />;
}

 

 

그러나 이미 존재하는 태그를 덮어씌워 반환해주는 이러한 기본 컴포넌트의 경우 그냥 사용하면 해당 태그가 원래 가지고 있던 타입 대신 따로 설정한 타입으로 오버라이딩 되어 타입 오류를 경험할 수 있습니다.

 

 

input의 기본 프로퍼티인 value를 찾지 못하고 있습니다.

 

 

위 사진처럼 원래의 input 태그가 가지고 있어야 할 value 타입 등을 찾을 수 없다고 에러 메시지가 나타나는데, 당연한 결과입니다. 우리가 Props를 넘겨주었던 CustomInput 컴포넌트의 InputProps에는 value가 존재하지 않으니까요.

그렇다면 해결 방법은 간단합니다. 해당 프로퍼티들을 함께 InputProp에 넣어주면 됩니다.

 

 

해결 방안

 

CustomInput에서 Input으로 다른 속성들까지 전달해주어야 합니다

 

 

 

이런 경우에 사용하기 좋은 타입이 있는데, 바로 React.DetailedProps 입니다.

 

 

type DetailedHTMLProps<E extends HTMLAttributes<T>, T> = ClassAttributes<T> & E;

 

 

 

DetailedProps의 경우 HTMLAttributes의 파생 타입을 제네릭으로 받아 해당 타입을 반환해줍니다. 따라서 위처럼 Input 태그의 속성들이 필요한 경우, 아래처럼 사용하면 Input 태그가 원래 가지고 있던 타입들을 가져올 수 있습니다.

 

 

React.DetailedHTMLProps<React.InputHTMLAttributes<HTMLInputElement>, HTMLInputElement>
// accept, alt, autoComplete, autoFocus, capture, checked ...

 

 

이제 앰퍼센트(&) 연산자를 이용해 커스텀 컴포넌트의 Props 타입을 우리가 따로 받아오고 싶었던 타입과 원래 태그가 가지고 있던 타입을 인터섹션 타입으로 만들어 함께 받아와줍니다.

 

 

const Input = ({
  isValid = true,
  hasUnderline = false,
}: InputProps &
  React.DetailedHTMLProps<React.InputHTMLAttributes<HTMLInputElement>, HTMLInputElement>) => {
  ...
}

 

 

타입을 불러왔으니 이제 속성들을 명시해 줄 차례입니다. 스프레드 연산자 (...) 를 이용해 구조분해 할당이 적용된 props 안쪽에도 나머지 속성들을 표시해줍니다.

 

 

const Input = ({
  isValid = true,
  hasUnderline = false,
  ...inputAttribute // 이름은 꼭 inputAttribute일 필요는 없습니다.
}

 

 

마지막으로 반환해주는 컴포넌트에도 해당 속성들을 내려주면 끝입니다.

 

 

return <S.Input isValid={isValid} {...inputAttribute} />;

 

 

 

이제 기본 타입도 잘 적용되는 모습입니다.

 

 

비단 기본 태그들에만 적용되는 케이스가 아니라, 본연의 props들을 가지고 있는 컴포넌트를 반환하는 컴포넌트를 새로 만들때도 이렇게 기존의 타입들을 챙겨주어야 오류를 방지할 수 있습니다.

반응형

'이론 > Frontend' 카테고리의 다른 글

웹 표준에 대한 고찰  (0) 2023.02.15
Web과 Ajax에 대하여  (1) 2022.12.30
Canvas API 사용해보기  (4) 2022.12.09
Context API 개념 잡기  (0) 2022.11.22
Recoil + React-query 삽질기  (6) 2022.10.28

댓글