Kembali ke Blog
Tutorial#typescript#javascript#tips#web development#2026

10 TypeScript Tips yang Bikin Kode Anda Lebih Bersih dan Aman di 2026

TypeScript sudah jadi standar di industri. Tapi banyak developer masih pakai TypeScript seperti JavaScript biasa. Ini 10 tips advanced yang benar-benar berguna di project nyata.

Muhamad Putra Aulia Hidayat

Muhamad Putra Aulia Hidayat

29 Maret 20264 menit baca

10 TypeScript Tips untuk Kode yang Lebih Bersih

Setelah hampir 2 tahun TypeScript jadi standar wajib di hampir semua project JavaScript serius, masih banyak developer yang belum menggunakannya secara optimal. Ini tips-tips yang benar-benar berguna.

1. Pakai satisfies bukan Type Assertion

// Buruk - as mematikan type checking
const config = {
  theme: "dark",
  port: 3000
} as AppConfig

// Lebih baik - satisfies tetap check tipe tapi pertahankan literal types
const config = {
  theme: "dark",
  port: 3000
} satisfies AppConfig

// Sekarang config.theme bertipe "dark" bukan string

2. Discriminated Union untuk State Management

// Buruk
interface ApiState {
  loading: boolean
  data?: User
  error?: string
}

// Baik - setiap state eksplisit dan type-safe
type ApiState =
  | { status: "idle" }
  | { status: "loading" }
  | { status: "success"; data: User }
  | { status: "error"; error: string }

function render(state: ApiState) {
  switch (state.status) {
    case "success":
      return state.data.name // TypeScript tahu data ada di sini
    case "error":
      return state.error // TypeScript tahu error ada di sini
  }
}

3. Template Literal Types

type HttpMethod = "GET" | "POST" | "PUT" | "DELETE"
type ApiRoute = "/users" | "/products" | "/orders"
type ApiEndpoint = `${HttpMethod} ${ApiRoute}`

// TypeScript akan autocomplete: "GET /users", "POST /products", dll
function callApi(endpoint: ApiEndpoint) { ... }

4. Infer dalam Conditional Types

// Extract return type dari promise
type Awaited<T> = T extends Promise<infer R> ? R : T

// Extract parameter types
type FirstParam<T extends (...args: any) => any> =
  T extends (first: infer F, ...rest: any) => any ? F : never

// Contoh penggunaan
async function fetchUser(): Promise<User> { ... }
type UserType = Awaited<ReturnType<typeof fetchUser>> // User

5. Mapped Types untuk Transformasi

// Buat semua property opsional tapi hanya satu level
type PartialOne<T> = { [K in keyof T]?: T[K] }

// Buat semua property readonly dan required
type Frozen<T> = { readonly [K in keyof T]-?: T[K] }

// Buat type baru dengan rename key
type Getters<T> = {
  [K in keyof T as `get${Capitalize<string & K>}`]: () => T[K]
}

interface User { name: string; age: number }
type UserGetters = Getters<User>
// { getName: () => string; getAge: () => number }

6. Const Assertions untuk Config

// Tanpa const assertion
const ROLES = ["admin", "user", "moderator"]
// Tipe: string[]

// Dengan const assertion
const ROLES = ["admin", "user", "moderator"] as const
// Tipe: readonly ["admin", "user", "moderator"]

type Role = typeof ROLES[number]
// Tipe: "admin" | "user" | "moderator"

7. Branded Types untuk Keamanan

// Masalah: ID yang berbeda tapi sama-sama string
function getUser(userId: string) { ... }
function getProduct(productId: string) { ... }

// Tidak ada yang cegah: getUser(productId) -- bug!

// Solusi: Branded types
type UserId = string & { readonly __brand: "UserId" }
type ProductId = string & { readonly __brand: "ProductId" }

function createUserId(id: string): UserId {
  return id as UserId
}

function getUser(userId: UserId) { ... }
// getUser(productId) sekarang error TypeScript!

8. Exhaustive Checks

type Shape = "circle" | "square" | "triangle"

function getArea(shape: Shape, size: number): number {
  switch (shape) {
    case "circle": return Math.PI * size ** 2
    case "square": return size ** 2
    case "triangle": return (Math.sqrt(3) / 4) * size ** 2
    default:
      // Kalau ada Shape baru yang belum di-handle, TypeScript error di sini
      const _exhaustive: never = shape
      throw new Error(`Unhandled shape: ${_exhaustive}`)
  }
}

9. Pakai unknown bukan any

// Buruk - any mematikan semua type checking
function processData(data: any) {
  data.nonExistentMethod() // Tidak ada error, bug tersembunyi
}

// Baik - unknown paksa kamu validasi dulu
function processData(data: unknown) {
  if (typeof data === "object" && data !== null && "name" in data) {
    console.log((data as { name: string }).name)
  }
}

10. Strict Mode Full

Pastikan tsconfig.json kamu punya:

{
  "compilerOptions": {
    "strict": true,
    "noUncheckedIndexedAccess": true,
    "exactOptionalPropertyTypes": true,
    "noImplicitReturns": true,
    "noFallthroughCasesInSwitch": true
  }
}

strict: true saja tidak cukup — noUncheckedIndexedAccess sangat berguna untuk mencegah bug saat akses array/object dengan index dinamis.

Semua tips di atas sudah kami terapkan di semua project Digital Uptime. Hasilnya: lebih sedikit bug di production dan onboarding developer baru jadi lebih mudah.

typescriptjavascripttipsweb development2026

Newsletter Digital Uptime

Tips teknologi & bisnis mingguan

Bergabung dengan 2,500+ subscriber yang mendapatkan insight teknologi, tutorial development, dan tips bisnis digital langsung ke inbox mereka setiap minggu.

Tidak ada spam. Unsubscribe kapan saja.

Artikel Terkait

Kami menggunakan cookies untuk meningkatkan pengalaman Anda di website ini. Dengan melanjutkan, Anda menyetujui penggunaan cookies sesuai Kebijakan Privasi kami.