Typescript

satisfies 키워드란?

bkdragon 2023. 7. 2. 15:17

Upcasting과 Downcasting

부모 자식 상속관계의 클래스가 있을 때,

  • Upcasting : 자식 → 부모 방향으로 형변환하는 것.
  • Downcasting : 부모 → 자식 방향으로 형변환하는 것.

타입에도 적용되는 개념이다.

 

 

const variable = 10

위 코드를 타입스크립트는 다음과 같은 순서로 추론한다.

  1. variable 의 type을 알 수 없다.
  2. 10 은 number type을 가지는 literal이다.
  3. variable 은 number literal이 할당 되므로 number type이다.

 

 const variable = { grade: "a", score: 90 }

위 코드는 다음과 같은 순서로 추론된다.

  1. variable 의 type 을 알 수 없다.
  2. { grade: "a", score: 90 }{ grade: string, score: number} type 을 가지는 literal 이다.
  3. variable 은 literal이 할당 되므로 { grade: string, score: number } type 이다.

위 두 코드의 과정을 보면 upcasting 이 발생하고 있는 것으로 볼 수 있다. literal(구체적인 하위 타입)에서 원시 타입 (일반 적인 상위 타입)으로 변환되어 추론되고 있다.

 

 

satisfiles 란?

satisfies는 객체 literal을 안전하게 upcating 해준다. 안전하게라는 의미는 객체 리터럴의 정보가 보존된다는 뜻이다.

그냥 타입을 정의하는 것과 무슨 차이가 있는 거지 하는 의문이 들 수 있다. 예시를 통해 살펴보자.

우선 타입 정의를 이용한 경우를 보자.

const palette : Record<'red' | 'green' | 'blue', [number, number, number] | string> = {
    red: [255, 0, 0],
    green: "#00ff00",
    blue: [0, 0, 255], 
}

value는 number 배열이 될 수도 있고 단순히 string이 될 수 도 있다.

palette.blue에 접근한다고 했을 때, 다음과 같은 상황에 놓인다.

 

 

satisfiles를 이용한다면?

const palette  = {
    red: [255, 0, 0],
    green: "#00ff00",
    blue: [0, 0, 255], 
} satisfies Record<'red' | 'green' | 'blue', [number, number, number] | string>

아무 이상이 없다.

 

 

value의 타입을 살짝 바꿔보자 string → number

const palette  = {
    red: [255, 0, 0],
    green: "#00ff00",
    blue: [0, 0, 255], 
} satisfies Record<'red' | 'green' | 'blue', [number, number, number] | number> 

지정된 타입이 아니라면 오류도 뱉어준다.

 

 

만약 value가 unknown이라면?

보이는가 blue key의 타입을 array로 추론하고 메서드가 자동완성에 포함된다.

 

 

즉, 타입 정의를 이용하면 객체 리터럴의 key의 타입 제한을 할 수 없지만 satisfies를 이용하면 객체 리터럴의 정보를 보존하여 key의 타입 제한이 가능하다.