[TS] Double assertion

장동균·2022년 10월 23일
0
post-custom-banner

https://basarat.gitbook.io/typescript/type-system/type-assertion#double-assertion
해당 글을 제가 이해하기 좋게 번역한 글입니다.


배경

function handler (event: Event) {
    let mouseEvent = event as HTMLElement;
}

typescript에서 as 키워드는 대상을 특정한 타입으로 강제한다.

하지만, 해당 코드는 Error: Neither 'Event' nor type 'HTMLElement' is assignable to the other 에러가 발생한다.

타입을 강제하는 as 키워드를 썼음에도 불구하고 왜 에러가 발생하는 것일까?


이유

기본적으로 A as B 를 사용하기 위해서는 A가 B의 subtype이거나, B가 A의 subtype이어야 한다. 완전한 타입 강제는 너무나도 위험하기 때문에 타입스크립트에서는 as 키워드에 최소한의 안전장치를 갖추어 둔 것이다.

EventHTMLElement의 subtype이 아니며, 당연히 HTMLElementEvent의 subtype이 아니다. 때문에 위 구문은 기본적인 as 키워드의 원칙을 위배했고 이로 인해 에러가 발생하는 것이다.


해결

모든 타입을 포함하는 unknown 타입을 이용하여 이 문제를 해결할 수 있다.

A as unknown => A는 unknown의 subtype

unknown as B => B는 unknown의 subtype

A as unknown as B => A는 unknown, unknown은 B의 supertype

이를 통해 위의 구문은 다음과 같이 해결할 수 있다.

function handler (event: Event) {
    let mouseEvent = event as unknown as HTMLElement;
}

as any as vs as unknown as

위험하기는 둘 다 위험하다. 둘 중에 아무거나 선택해서 쓰면 된다고 하는데 그래도 보통 any 보다는 unknown을 선호하니까 unknown을 사용하는 편이 좋겠다.


참고문헌

https://basarat.gitbook.io/typescript/type-system/type-assertion#double-assertion
https://stackoverflow.com/questions/69399211/typescript-why-does-as-unknown-as-x-work

profile
프론트 개발자가 되고 싶어요
post-custom-banner

0개의 댓글