TypeScript를 처음 접할 때 가장 혼동되는 타입이 any, unknown, never 입니다. 모두 특별한 의미를 가진 타입으로, TypeScript의 타입 시스템을 깊이 이해하기 위해 반드시 익혀야 하는 중요한 요소입니다.
any - 타입 검사를 끄는 위험한 타입
any는 “어떤 타입이든 허용한다”는 의미로, TypeScript의 타입 검사를 완전히 우회합니다. 즉, JavaScript처럼 자유롭게 값을 넣을 수 있지만, 타입 안전성을 잃어버립니다.
let value: any = 123;
value = "hello";
value = true;
value = {};
value.nonExistMethod(); // ❗ 컴파일 시 오류 없음 → 런타임에서 터짐
any를 사용하면 좋은 경우
- 정말 타입을 알 수 없고 빠르게 프로토타입을 만들 때
- 기존 JavaScript 코드를 TypeScript로 점진 이동하는 초기 단계
- 서드파티 라이브러리가 타입 정보를 제공하지 않을 때
any를 사용하면 위험한 이유
- IDE 자동완성·타입 검사 기능 사라짐
- 코드 품질·가독성 저하
- 런타임 오류 증가
- 프로젝트 전체에 타입 불안정성 확산
실무에서는 any 남용 = 유지보수 지옥으로 직결되므로 지양해야 합니다.
unknown - any보다 안전한 “모르는 타입”
unknown은 “타입을 알 수 없다”는 뜻은 동일하지만, any와 결정적으로 다른 점은 unknown 값은 바로 사용할 수 없다는 것입니다.
let data: unknown = "hello";
data.toUpperCase();
// ❌ 오류: unknown은 바로 사용 불가능
사용하려면 먼저 타입 체크가 필수입니다.
if (typeof data === "string") {
console.log(data.toUpperCase()); // ✔ 안전하게 사용 가능
}
unknown이 any보다 좋은 이유
unknown은 다음과 같은 장점을 가집니다.
- 타입 체크가 강제되므로 런타임 오류 감소
- 타입 보호(Type Guard)가 필수 → 코드의 안정성 증가
- 외부 API 응답 타입처럼 "정확히 알 수 없는 값"을 다룰 때 적합
추천되는 사용 사례
- JSON 파싱 결과 처리
- 외부 API, 메시지 큐에서 넘어오는 데이터
- 사용자 입력(form, CLI, 이벤트 등)
function parseJson(json: string): unknown {
return JSON.parse(json);
}
unknown은 실무에서 “타입을 알 수 없는 경우 but any는 쓰기 싫은 경우” 최선의 선택입니다.
never - 절대 발생할 수 없는 타입
never는 “값이 존재할 수 없다”는 뜻으로, TypeScript에서 가장 특수한 타입입니다. 다음과 같은 상황에서 never가 발생합니다.
1. 항상 오류를 발생시키는 함수
function throwError(msg: string): never {
throw new Error(msg);
}
2. 무한 루프 함수
function infinite(): never {
while (true) {}
}
3. 타입 좁히기(Narrowing)에서 모든 경우가 처리된 후 남는 타입
type Shape = "circle" | "square";
function draw(shape: Shape) {
if (shape === "circle") {
// ...
} else if (shape === "square") {
// ...
} else {
const neverValue: never = shape;
// ❌ shape가 never가 아니면 오류 → 모든 case가 처리되었음을 보장
}
}
이 패턴은 실무에서 switch-case exhaustive 체크에 매우 유용합니다.
세 타입 비교 요약
| 타입 | 설명 | 특징 | 사용 권장 여부 |
|---|---|---|---|
| any | 모든 타입 허용 | 타입 검사 없음 → 위험 | 가급적 사용 금지 |
| unknown | 타입을 알 수 없음 | 사용 전 타입 체크 필요 → 안전 | 추천 |
| never | 값이 존재할 수 없음 | 오류/무한루프/타입 좁히기에서 사용 | 특별한 상황에서만 사용 |
실무 상황별 정리
1) 외부 입력 값 → unknown
function handleInput(input: unknown) {
if (typeof input === "string") {
// 안전하게 문자열로 처리
}
}
2) 초기 개발 단계 → any(최소 사용 권장)
let temp: any; // 점진적 마이그레이션 시 사용 가능
3) 모든 경우의 수를 처리해야 할 때 → never
function assertNever(value: never): never {
throw new Error("Unhandled case: " + value);
}
4) 기획 변경으로 enum 값이 늘어날 때 자동 감지 → never 활용
이 패턴은 서비스 규모가 커질수록 매우 유용합니다.
any, unknown, never는 TypeScript의 타입 시스템에서 매우 중요한 역할을 합니다. 각각의 목적이 분명히 다르며, 제대로 사용하면 코드의 안전성과 유지보수성을 획기적으로 개선할 수 있습니다.
- any는 마지막 수단, 타입 안전성을 포기하는 선택
- unknown은 “안전한 any”, 가장 추천되는 대체 타입
- never는 특정 상황에서 타입 검사 강화
'개발 > Typescript' 카테고리의 다른 글
| [TYPESCRIPT] 타입 추론(Type Inference) 이해하기 - TypeScript가 똑똑하게 타입을 결정하는 방법 (0) | 2025.11.25 |
|---|---|
| [TYPESCRIPT] 객체 타입 정의하기 - TypeScript의 구조적 타입 시스템 완전 이해 (0) | 2025.11.23 |
| [TYPESCRIPT] 배열과 튜플 다루기 - TypeScript에서 컬렉션을 안전하게 사용하는 방법 (0) | 2025.11.22 |
| [TYPESCRIPT] 기본 타입 소개 - string, number, boolean 완벽 이해하기 (0) | 2025.11.21 |
| [TYPESCRIPT] tsconfig.json 완벽 가이드 - TypeScript 프로젝트 설정의 모든 것 (0) | 2025.11.20 |
