Typescript의 유틸리티 타입 (1) - Record, Exclude, Extract, Pick

ggong·2021년 7월 6일
17

타입스크립트를 야금야금 조금씩 알아봅시당!

React-hook-form이 지원하는 field의 타입을 알아보다가 한 팀원분의 추천으로 깃헙 코드를 찾아보게 되었다. 안에서 TS의 유틸리티 타입을 사용하는 곳이 많아서, 조금씩 찾아보다가 블로그에 정리하면 좋겠다고 생각했다. 물론 한꺼번에 다는 기억 못할 것 같으니까 나눠서 올릴 예정.

1) Record<K, T>

Record 타입은 두 개의 제네릭 타입을 받을 수 있다.
첫번째 제네릭 타입 K는 key 값의 타입으로, 두번째 제네릭 타입 T은 값의 타입으로 갖는 타입을 리턴한다.

type Record<K, T> = {
    [P in K]: T;
};

프로퍼티 키 값을 K 타입으로, 값을 T 타입으로 하는 타입을 만들 수 있다.

type IFieldValue = {
  name: string;
  value: number;
};

type IFormName = 'event' | 'point';

const x: Record<IFormName, IFieldValue> = {
  event: {
    name: 'foo',
    value: 0,
  },
  point: {
    name: 'foo',
    value: 30,
  }
}

2) Exclude<T, U>

Exclude 타입은 2개의 제네릭 타입을 받을 수 있으며,
첫번째 제네릭 타입 T 중 두번째 제네릭 타입 U와 겹치는 타입을 제외한 타입을 반환한다.

type Exclude<T, U> = T extends U ? never : T;

타입 T가 타입 U를 상속하거나 동일 타입이라면 무시(never)하고 아닐 경우 타입 값을 리턴한다.

type OnlyNumber = Exclude<string|number, string>;
// OnlyNumber는 number 타입이다.

다시 말해 두번째 제네릭 타입 U에 대해
첫번째 제네릭 타입 T가 할당 가능한 타입인지를 판단하고,
할당 가능한 타입을 제외한 나머지 타입들을 이용하여 타입을 정의한다.

3) Extract<T, U>

첫번째 제네릭 타입 T에 대하여 제네릭 타입 U 중 할당 가능한 타입을 할당한다. Exclude와 반대되는 개념이다.

type Extract<T, U> = T extends U ? T : never;

T 타입에서 U 타입과 겹치는 타입만을 추출한다.

type Event = {
  id: string;
  title: string;
};

type Point = {
  target: string;
  amount: number;
};

type PointInfo = Extract<Event|Point, Point>;
// PointInfo 타입과 Point 타입은 동일한 타입이다.

Exclude 타입과는 다르게 유니온 타입 Event와 Point에 대하여 Point 할당 타입을 반환하기 때문에 PointInfo 타입은 Point 타입과 같아진다. 내가 원하는 프로퍼티로 구성된 타입이 이미 있을 때 사용할 수 있을거 같다.

4) Pick<T, K>

T 타입으로부터 K 프로퍼티만 추출한다.

type Pick<T, K extends keyof T> = {
    [P in K]: T[P];
};

주어진 첫번째 제네릭 타입 T 내에서 Union 타입 K라는 프로퍼티에 대한 타입들을 뽑아낸다.
필요한 타입만 추출해서 원하는 타입을 만들 수 있다.

interface Event {  
  id: string;
  title: string;
  isDone: boolean;
  startDate: string;
};

type BaseInfo = Pick<Event, 'id' | 'title'>;

interface PickedEvent {
  id: string;
  title: string;
};
// BaseInfo 타입과 PickedEvent 타입은 동일한 타입이다.

지금 작업하는 프로젝트에서 이벤트 정보에 대한 타입을 엄청 많이 들고 있고, 이 중에 일부 데이터만 사용하는 부분이 있다. 이럴 경우 만약 내가 필요한 프로퍼티들을 한번에 지정해놓은 타입이 있다면 Extract를 사용하고, 아니라면 Pick<이벤트 타입, 원하는 key> 형태로 가져오면 손쉽게 필요한 타입들만 쓸 수 있겠다는 생각이 들었다.



참고 :
Typescript의 기본 유틸 타입
(https://blog.martinwork.co.kr/typescript/2019/05/28/typescript-util-types.html)

profile
파닥파닥 FE 개발자의 기록용 블로그

2개의 댓글

comment-user-thumbnail
2022년 3월 31일

감사합니다

답글 달기
comment-user-thumbnail
2023년 9월 6일

잘 읽었어요!

답글 달기