728x90

Index Type

좀 더 유연한 설계를 위해서 interface를 만들 때 key 값을 런타임 환경에서만 알 수 있을 때 대처하기 위해서 index type을 사용

 

// { email: 'Not a valid email', username: 'Must start with a charcter!' }
interface ErrorContainer {
  [prop: string]: string;
}

const errorBag: ErrorContainer = {
  error: "Not a valid email",
  username: "Must start with a charcter!",
};

 

error tag 를 key로 가지고 error message를 value로 가지는 interface type을 만들고 싶다.

하지만 컴파일 할땐 이 key 이름을 도저히 알 방법이 없다.

 

그래서 [prop: string]을 key 값으로 주고 어떤 key 값이 들어오더라도 string 이면 OK 하는 것이다.

 

Function Overloads (함수 오버로드)

type Combinable = string | number;
type Numeric = number | boolean;

type Universal = Combinable & Numeric;

function add(a: Combinable, b: Combinable): Combinable {
  if (typeof a === "string" || typeof b === "string") {
    return a.toString() + b.toString();
  }
  return a + b;
}

const result = add("ha", "jongyun");
result.split(""); // Error: type Combinable

 

위와 같은 코드에서 우리는 result 의 변수의 값이 string이라는 것을 유추할 수 있다.

하지만 타입 추론에서는 Combinalbe 타입 이라는 것을 유추하여 result  변수에 string 타입이 가지는 메서드를 사용하면 에러가 발생한다.

 

const result = add("ha", "jongyun") as string;
result.split("");

 

타입 캐스팅을 사용하여 타입을 명시적으로 변환해도 상관 없지만 함수를 호출할 때마다 타입 캐스팅을 해줘야 하는 번거로움이 있고

좀 더 복잡한 로직이 들어가면 어떤 타입으로 캐스팅해줘야 할지 모르는 경우도 있다.

 

함수 오버로드를 사용하여 이문제를 해결한다.

 

function add(a: number, b: number): number;
function add(a: string, b: string): string;
function add(a: Combinable, b: Combinable): Combinable {
  if (typeof a === 'string' || typeof b === 'string') {
    return a.toString() + b.toString();
  }
  return a + b;
}

const result = add('ha', 'jongyun');
result.split('');

 

오버로드가 1개 더 있다고 나오고 result 타입이 string 이라는 것을 잘 유추해서 split 메서드를 사용해도 에러가 나지 않는다.

 

 

 

Optional Chaining

Api 를 통해 유저 데이터를 가져오는 경우 특정 데이터가 response 될지에 대해서 100% 확신할 수 없다.

 

const fetchUserData = {
  id: "u1",
  name: "Max",
  // job: { title: "CEO" },
};

console.log(fetchUserData.job.title);

 

우린 분명 job 이라는 key 안에 object 가 전달될 거라고 예상했지만 서버에서 응답 오류로 job이라는 key와 object value 가 손실되었다.

 

그렇게 되면 분명 console.log 는 런타임 에러가 발생한다.

런타임 에러를 막기 위해 이런 코드를 많이 사용한다.

console.log(fetchUserData.job && fetchUserData.job.title);

 

 

이 방법도 훌륭한 방법이다. 하지만 typescript ES7 에서는? 연산자 optional chaining을 지원한다.

console.log(fetchUserData?.job?.title);

 

? 앞에 있는 것이 정의되어 있지 않은 경우에는 뒤에 있는 것에 액세스 하지 않는다.

이로써 런타임 에러를 막을 수 있다.

 

타입 스크립트를 사용하는 장점 중 하나가 자바스크립트 코드에서 많은 런타임 에러들을 컴파일 단계에서 많이 잡을 수 있다는 것이다.

 

 

 

Nullish Coalescing (무효화 합체)

Nullish Coalescing라는 뜻이 어떤 뜻인지 알기 위해서는 일단 자바스크립트에서 동작하는 falsy 한 값에 대해 알아야 한다.

 

자바스크립트는 빈 문자열, 0, null, undefined에 대해서 false 하다고 판단하여 if 문 과같은 곳에서 boolean으로 비교한다면 false와 같이 동작한다.

 

const userInput = "";

 

유저의 정보를 입력하는 태그가 있다고 가정하자. 하드 코딩되어 있지만 데이터를 가져왔다고 상상해보자

개발자의 의도에 의해서 정말 빈 문자열을 허용하고 싶을 때도 있다. 선언이 되지 않았거나 null 값일 때만 기본 값으로 대체하고 싶을 땐

어떻게 해야 할까?

 

const storedData = userInput ?? "DEFAULT";

 

?? 연산자는 null과 undefined에 대해서만 fall back 한다. 0이나 빈 문자열에 대해서는 참으로 인식한다는 것이다.

그렇게 많이 쓸 일은 없을 것 같지만 알아두면 좋을 것 같다.

728x90

'TypeScript' 카테고리의 다른 글

Typescript Generic programing  (0) 2021.11.29
Advanced Typescript - 타입스크립트 좀더 깊게 알아보기  (0) 2021.11.28
Typescript Interface  (0) 2021.11.28
Typescript Class  (0) 2021.11.27
typeorm database migration  (0) 2021.06.24