Bölüm 5: Union, Intersection ve Literal Types

TypeScript’in belki de en güçlü, en “gerçek dünya” odaklı konularından biri olan Union Types, Intersection Types ve Literal Types konularına geldik.
Bu konular, özellikle React component varyasyonlarında, durum yönetiminde, API veri modellemelerinde ve form yapılarında çok sık kullanılır. Şimdi bu bölümü tamamen açıklamalı, öğretici ve örnekli bir şekilde işleyelim.
Bu bölümde neler öğreneceğiz?
- Union Type (
|
) nedir, nasıl kullanılır? - Intersection Type (
&
) nedir, ne zaman gerekir? - Literal Type nedir, neden çok işlevseldir?
- Discriminated Union: tip güvenli durum kontrolü nasıl kurulur?
- Tüm yapılar nasıl React veya API modellerinde uygulanır?
5.1 Union Type (|
)
Tanım: Union type bir değişkenin birden fazla farklı tipten birini alabileceğini belirtir.
1let value: string | number;23value = "Merhaba"; // ✅4value = 42; // ✅5value = true; // ❌ TS Error
Gerçek Kullanım:: Kullanıcıdan gelen bir input değeri olabilir:
1function formatInput(input: string | number): string {2return input.toString().toUpperCase();3}
❗ Yukarıdaki kod hata verir çünkü number.toUpperCase()
yoktur.
✅ Doğrusu:
1function formatInput(input: string | number): string {2if (typeof input === "string") {3return input.toUpperCase();4}5return input.toString();6}
✅ Type Guard kullanmadan union type'lar doğrudan kullanılamaz. TypeScript emin olmak ister.
5.2 Intersection Type (&
)
Tanım: Intersection type, birden fazla tipin birleştirilmesi ile oluşur. Tüm alanlara birlikte sahip olmalıdır.
1type Name = { name: string };2type Age = { age: number };34type Person = Name & Age;56const person: Person = {7name: "Yasin",8age: 26,9};
Nerede kullanılır?
- API modellerini birleştirmek için
props
vestyle
gibi iki farklı veri kaynağını birleştirmek için- React’te
props: ComponentProps & StyleProps
gibi kullanım
5.3 Literal Types
Tanım: Literal type, değeri sabitlenmiş tiplerdir.
1type Direction = "up" | "down" | "left" | "right";23let move: Direction;45move = "up"; // ✅6move = "down"; // ✅7move = "back"; // ❌ TS Error
Gerçek Kullanım:
1type ButtonVariant = "primary" | "secondary" | "danger";23function renderButton(variant: ButtonVariant) {4return `<button class="${variant}">${variant}</button>`;5}
✅ Kod daha okunaklı, hatasız ve otokompletesi güçlü olur.
5.4 Discriminated Union – Duruma Göre Tip Seçimi
Tanım: Aynı yapıya sahip ama farklı davranışlar içeren tipleri, ortak bir discriminator
alanı ile ayırarak tip güvenli kontrol yapılmasını sağlar.
Örnek: API veri durumu
1type Loading = { status: "loading" };2type Success = { status: "success"; data: string };3type Error = { status: "error"; errorMessage: string };45type ApiState = Loading | Success | Error;
Kullanım:
1function renderState(state: ApiState) {2switch (state.status) {3case "loading":4return "Yükleniyor...";5case "success":6return `Veri: ${state.data}`;7case "error":8return `Hata: ${state.errorMessage}`;9}10}
✅ TypeScript burada status
alanına göre hangi objenin geldiğini otomatik olarak anlar ve uygun alanlara erişime izin verir.
5.5 Union & Literal Types ile Form Alanı Kontrolü
1type FieldType = "text" | "number" | "checkbox";23type FormField = {4name: string;5type: FieldType;6};78const field: FormField = {9name: "Kullanıcı Adı",10type: "text"11};
❌ type: "dropdown"
verirsen anında hata alırsın. Çünkü "dropdown"
FieldType
içinde yok.
5.6 Union ve Intersection Ne Zaman Kullanılır?
Kullanım Durumu | Yapı |
---|---|
Birden fazla farklı durumdan sadece biri | Union (|) |
Tüm özellikleri birleştirmek | Intersection (&) |
Sadece belirli değerleri kabul etmek | Literal Type |
Durumlara özel davranış sergilemek | Discriminated Union |
Gerçek Uygulama: Buton Bileşeni Varyasyonu
1type Variant = "primary" | "secondary" | "danger";23type ButtonProps = {4text: string;5variant: Variant;6};
1function Button({ text, variant }: ButtonProps) {2const classMap: Record<Variant, string> = {3primary: "bg-blue-500 text-white",4secondary: "bg-gray-200 text-black",5danger: "bg-red-500 text-white",6};78return <button className={classMap[variant]}>{text}</button>;9}
Alıştırmalar
Status = "idle" | "loading" | "error" | "success"
union’ı tanımla, bir fonksiyon yaz ve switch-case ile her durumu işle.type Admin = { role: "admin"; privileges: string[] }
vetype User = { role: "user"; group: string }
union yapısıyla birleşmişPerson
tipi oluştur.type Theme = "light" | "dark" | "system"
ile çalışan bir fonksiyon yaz.
Bölüm Özeti
Yapı | Açıklama |
---|---|
Union (|) | Birden fazla tipten biri olabilir |
Intersection (&) | Tüm özellikleri taşıyan tip |
Literal Types | Sabit değer tipi |
Discriminated Union | Ortak bir alanla ayrılmış union yapıları |
Kullanım alanları | Durum kontrolü, component varyasyonları, API modelleme |
Bu Bölümle Artık:
- Bir değişkenin alabileceği değerleri sınırlayabiliyorsun.
- Tip güvenli switch-case yapıları kurabiliyorsun.
- React bileşenlerini varyasyonlarla genişletebiliyorsun.
- API, form ve state yapılarında çok daha sağlam veri modelleri oluşturabiliyorsun.