Section 1/91 menit

1. Masalah yang Dipecahkan

1. Masalah yang Dipecahkan

Error Handling di Swift 5: Kehilangan Informasi Tipe

Sebelum Swift 6, throws adalah untyped — compiler tidak tahu dan tidak peduli error apa yang dilempar. Semua error diperlakukan sebagai any Error:

swift
// Swift 5: apa pun bisa keluar dari sini
func parseJSON(_ data: Data) throws -> User {
    // Bisa lempar: DecodingError, NetworkError, CustomError, apapun
}

// Caller terpaksa menebak atau catch-all:
do {
    let user = try parseJSON(data)
} catch let error as DecodingError {
    // mungkin ini
} catch let error as NetworkError {
    // mungkin ini
} catch {
    // atau apapun yang lain — ini selalu dibutuhkan
    // karena compiler tidak tahu apa yang mungkin dilempar
}

Masalah nyata dari untyped throws:

  1. False safety: Kamu bisa menangkap tipe error yang salah dan compiler tidak memperingatkanmu
  2. Documentation rot: Dokumentasi "throws NetworkError" bisa berbohong — compiler tidak enforces ini
  3. Overhead runtime: Error selalu di-box sebagai existential any Error — ada heap allocation
  4. Library design: Library tidak bisa mengekspresikan "fungsi ini HANYA bisa lempar tipe X"
  5. Generic functions: Tidak bisa menulis map yang meneruskan error type dari transform ke caller
swift
// Swift 5: ini compile, bahkan jika parseJSON tidak pernah lempar NetworkError
do {
    let user = try parseJSON(data)
} catch let error as NetworkError {
    // block ini tidak pernah dieksekusi, tapi compiler tidak tahu itu
    handleNetworkError(error)
}

Apa yang Diinginkan Developer

Yang diinginkan adalah ekspresi yang jujur dan verifiable di compile time:

  • "Fungsi ini hanya bisa lempar NetworkError"
  • "Fungsi ini tidak bisa lempar sama sekali"
  • "Fungsi generic ini meneruskan error type dari parameter-nya"