"as const 는 한 keyword 의 3 기능: readonly, narrow, tuple. 값이 정확히 자기 자신이길 원할 때마다 써."
as const 가 뭐 함
as const assertion 이 적용된 어떤 거든 3가지 동시에 함:
- 모든 값이 widening 된 타입에서 literal 타입으로 narrow.
string대신'red'.number대신42.boolean대신true. - 모든 property 가 readonly 됨. Object property 가
readonlymodifier 얻고; 배열이 readonly 배열 됨. - 배열 literal 이 단일 element 타입의 (가변 길이) 배열 대신 (고정 길이, 위치별 타입의) tuple 됨.
결합 효과: 값의 타입이 정확히 자기 모양 됨, widening 없이, mutation 없이, 유연성 없이. "이 정확한 거 진짜로 의미" 의 가장 강한 형태.
손 뻗을 때
1. 고정 configuration object. const ROUTES = { CHAT: '/chat', LOGIN: '/login' } as const — 모든 값이 literal string 타입 되고, object 가 mutate 못 됨. 나중에 함수 parameter 를 route: typeof ROUTES[keyof typeof ROUTES] 로 타입 붙이면, 실제 route 문자열의 literal union 얻어.
2. 고정 상수 list. const COLORS = ['red', 'green', 'blue'] as const — 배열이 readonly ['red', 'green', 'blue'], literal 타입의 tuple. typeof COLORS[number] 가 literal union 'red' | 'green' | 'blue' 줘.
3. Literal-union parameter 가진 함수에 전달되는 object literal. as const 없으면, { method: 'POST' } 가 { method: string } 추론, { method: 'GET' | 'POST' } 타입 parameter 만족 못 함. as const 추가하면 property 가 literal 타입 되고, 호출 type-check 통과.
as const 가 그렇게 말하는 방법. Widening 괜찮으면 (값이 mutate 되거나 reassign 될 거라서) 뺘.typeof 와 결합 패턴
as const 가 값에서 타입 derive 할 때 빛나. const ROLES = ['admin', 'editor', 'viewer'] as const 가 readonly tuple 줘. 그다음 type Role = typeof ROLES[number] 가 literal union 'admin' | 'editor' | 'viewer' 줘. 이제 runtime-iterable 이고 type-system-known 인 단일 진실 source 가져. 이 패턴이 TypeScript-aware codebase 어디서나 나타나.
피파의 고백
as const + typeof X[number] 패턴 써. Runtime 이 plain 배열 얻고; type system 이 literal union 얻고; 둘 다 한 선언에서. 패턴이 너무 유용해서 첫날에 배우길 권해.