TypeScript Infer dan Conditional Types
Definisi
infer adalah kata kunci di dalam conditional types untuk menangkap tipe di dalam kondisi, lalu memakainya di cabang true. Ini kunci untuk "membongkar" tipe yang dibungkus (Promise, array, function) tanpa menyebut tipe tersebut secara eksplisit.
Kapan dipakai
Pakai infer saat kamu ingin mengekstrak sebagian tipe:
Awaited<T>→ tipe hasil PromiseElementOf<T>→ tipe elemen arrayReturnType<T>→ tipe kembalian functionUnwrap<T>→ tipe di balikRef/Box
Jangan pakai untuk hal sederhana yang cukup T[] atau Promise<T> langsung.
Cara kerja
Ekstrak elemen array
type ElementOf<T> = T extends (infer U)[] ? U : never;
type A = ElementOf<string[]>; // string
type B = ElementOf<number[]>; // numberEkstrak return type
type Fn = (a: number) => string;
type R = Fn extends (...args: any[]) => infer U ? U : never; // stringEkstrak tipe Promise
type Unwrap<T> = T extends Promise<infer U> ? U : T;
type X = Unwrap<Promise<boolean>>; // boolean
type Y = Unwrap<Date>; // Date (bukan promise)Struktur alur
Loading diagram...
Contoh recursive unwrap
type DeepUnwrap<T> = T extends Promise<infer U>
? DeepUnwrap<U>
: T;
type Z = DeepUnwrap<Promise<Promise<number>>>; // numberCatatan implementasi
inferhanya boleh muncul di dalam cabang kondisi (extends ... ? ... : ...).- Bisa menangkap multiple:
T extends [infer A, infer B] ? ... : .... - Kalau pattern tidak cocok, beri fallback
neveratau tipe asli agar tidak tiba-tiba hilang. - Conditional types bisa recursive (seperti
DeepUnwrap), tapi batasi kedalaman agar compile tidak berat.
Kesalahan umum
- infer di luar conditional: syntax error,
inferharus di dalamextends. - Lupa fallback: cabang false mengembalikan
neverpadahal tipe asli masih berguna. - Terlalu dalam recursive: tipe jadi lambat di-compile dan sulit dibaca.
- Salah tempat infer: menangkap di posisi salah (misal argumen bukan return) sehingga hasil tidak sesuai ekspektasi.