18. Coding Standards: TypeScript, ESLint, Prettier

Penerapan standar pengkodean (coding standards) yang ketat sangat penting untuk menjaga kualitas kode, mencegah bug sebelum masuk ke tahap runtime, serta memastikan kolaborasi tim yang harmonis. Proyek di Bit Group Asia wajib menggunakan kombinasi TypeScript, ESLint, dan Prettier dengan aturan baku berikut.


A. TypeScript Standards

TypeScript digunakan tidak hanya sebagai penunjuk tipe (annotator), melainkan sebagai pilar utama type safety dan self-documenting code.

1. Larangan Penggunaan any (Zero Tolerance for any)

Penggunaan tipe any menihilkan semua manfaat TypeScript dan menyembunyikan potensi runtime error.

  • Aturan: Dilarang keras menggunakan any. Gunakan interface atau type yang eksplisit.
  • Alternatif: Jika tipe data benar-benar dinamis atau tidak diketahui sebelumnya (seperti respon dari API pihak ketiga), gunakan unknown. Developer wajib melakukan type guarding atau pengecekan tipe sebelum menggunakan variabel bertipe unknown.
// ❌ Salah (Bad Practice)
function handleData(payload: any) {
  console.log(payload.user.name); // Potensi runtime error jika user undefined
}

// ✅ Benar (Best Practice)
interface UserPayload {
  user: {
    name: string;
    email: string;
  };
}

function handleData(payload: UserPayload) {
  console.log(payload.user.name); // Type-safe dan auto-complete aktif
}

// ✅ Benar dengan Type Guarding (untuk input dinamis)
function processValue(val: unknown) {
  if (typeof val === "string") {
    console.log(val.toUpperCase()); // Aman dilakukan setelah type guard
  }
}

2. Deklarasi Props Komponen & API Payloads secara Eksplisit

Setiap komponen React wajib mendefinisikan tipe data untuk props-nya.

  • Gunakan interface untuk mendefinisikan struktur objek (objects/props) yang dapat diekstensi.
  • Gunakan type untuk tipe data kombinasi (union types), tuple, atau alias tipe primitif.
// ✅ Contoh Interface untuk Props Komponen
interface ButtonProps {
  label: string;
  variant?: "primary" | "secondary" | "danger"; // Union type
  onClick: () => void;
  disabled?: boolean;
}

export const Button = ({ label, variant = "primary", onClick, disabled }: ButtonProps) => {
  return (
    <button onClick={onClick} disabled={disabled} className={`btn btn-${variant}`}>
      {label}
    </button>
  );
};

3. Wajib Mengaktifkan strict: true di tsconfig.json

Semua proyek wajib menyertakan flag strict di konfigurasi TypeScript untuk memaksa pengecekan tipe yang lebih disiplin. Beberapa sub-flag penting yang diaktifkan secara otomatis oleh strict: true:

  • noImplicitAny: Mencegah variabel bertipe any secara implisit jika tipe tidak ditentukan.
  • strictNullChecks: Memaksa pengecekan nilai null dan undefined secara eksplisit sebelum properti diakses.
  • strictFunctionTypes: Menjamin pemeriksaan tanda tangan fungsi (function signatures) yang lebih aman.
// tsconfig.json
{
  "compilerOptions": {
    "strict": true,
    "noImplicitAny": true,
    "strictNullChecks": true,
    "noUnusedLocals": true,
    "noUnusedParameters": true
  }
}

4. Penggunaan Utility Types secara Efisien

Manfaatkan Utility Types bawaan TypeScript untuk menghindari duplikasi tipe:

  • Pick<T, K>: Mengambil subset properti dari tipe lain.
  • Omit<T, K>: Membuang subset properti dari tipe lain.
  • Partial<T>: Membuat seluruh properti menjadi opsional.
  • Record<K, T>: Mendefinisikan tipe objek dengan key dan value bertipe tertentu.
interface User {
  id: string;
  name: string;
  email: string;
  role: "admin" | "member";
  createdAt: string;
}

// Mengambil hanya id dan name untuk daftar ringkas
type SimpleUser = Pick<User, "id" | "name">;

// Membuat payload update tanpa field id dan createdAt
type UpdateUserPayload = Partial<Omit<User, "id" | "createdAt">>;

B. ESLint Standards

ESLint bertindak sebagai penjaga gawang otomatis yang mendeteksi kesalahan sintaksis, anti-pattern, dan potensi bug statis.

1. Aturan Emas ESLint di Bit Group Asia

Setiap proyek wajib mengonfigurasi aturan linting minimum berikut untuk menjaga kekonsistenan penulisan kode:

  • @typescript-eslint/no-explicit-any: "error" ➔ Mencegah developer menulis tipe any secara sengaja.
  • no-unused-vars: "error" (atau "@typescript-eslint/no-unused-vars") ➔ Membersihkan variabel mati (dead code) yang tidak digunakan dari basis kode.
  • react-hooks/rules-of-hooks: "error" ➔ Memastikan aturan Hooks React dipatuhi (hanya dipanggil di tingkat atas).
  • react-hooks/exhaustive-deps: "warn" atau "error" ➔ Menjamin semua dependensi di hooks seperti useEffect atau useMemo dideklarasikan dengan benar untuk mencegah stale closures atau infinite rendering loops.
  • import/order: Mengharuskan pengurutan import secara otomatis agar file terlihat rapi (library eksternal di atas, absolute path @/* di tengah, file lokal ./ di bawah).

2. Menjalankan Linting

Developer wajib menjalankan perintah lint sebelum melakukan commit atau membuat Pull Request (PR):

# Memeriksa seluruh file dari kesalahan linting
npm run lint

# Memperbaiki kesalahan styling/formatting ESLint secara otomatis
npm run lint -- --fix

C. Prettier Standards

Prettier bertindak sebagai formatter kode yang konsisten, mengakhiri perdebatan gaya penulisan antar-developer (seperti tanda petik tunggal vs ganda, spasi vs tab, dll.).

1. Standar Konfigurasi Prettier (.prettierrc)

Seluruh proyek Bit Group Asia wajib menggunakan konfigurasi dasar Prettier berikut:

{
  "semi": true,
  "singleQuote": false,
  "tabWidth": 2,
  "useTabs": false,
  "trailingComma": "es5",
  "printWidth": 100,
  "bracketSpacing": true,
  "arrowParens": "always",
  "endOfLine": "lf"
}

Penjelasan Parameter Penting:

  • semi: true: Menggunakan titik koma (semicolon) di akhir setiap pernyataan untuk mencegah kesalahan interpretasi sintaks JS/TS.
  • singleQuote: false: Menggunakan tanda petik ganda (") sebagai standar penulisan string (selaras dengan default HTML).
  • tabWidth: 2: Spasi indentasi default adalah 2 spasi demi keterbacaan yang ringkas.
  • printWidth: 100: Membatasi lebar baris maksimal 100 karakter agar tidak perlu melakukan horizontal scrolling di layar standar.
  • trailingComma: "es5": Menambahkan koma menggantung pada objek/array sesuai standar ES5 untuk menjaga git diff tetap bersih saat ada penambahan item baru.

2. Menghindari Bentrokan ESLint & Prettier

Gunakan eslint-config-prettier untuk menonaktifkan semua aturan ESLint yang berkonflik dengan format formatting Prettier. Pastikan prettier di .eslintrc.json diletakkan paling akhir di bagian extends.

// .eslintrc.json
{
  "extends": [
    "next/core-web-vitals",
    "eslint:recommended",
    "plugin:@typescript-eslint/recommended",
    "prettier" // Wajib diletakkan di baris paling bawah untuk menimpa aturan formatting ESLint
  ]
}

D. Workflow & Automasi di Editor (VS Code)

Untuk meminimalkan waktu terbuang saat memperbaiki format secara manual, developer sangat direkomendasikan untuk mengonfigurasi auto-format pada editor masing-masing.

Konfigurasi VS Code Lokal (.vscode/settings.json):

Buat berkas .vscode/settings.json di dalam proyek agar konfigurasi ini otomatis aktif bagi seluruh developer yang membuka workspace:

{
  "editor.formatOnSave": true,
  "editor.defaultFormatter": "esbenp.prettier-vscode",
  "editor.codeActionsOnSave": {
    "source.fixAll.eslint": "explicit"
  },
  "[typescript]": {
    "editor.defaultFormatter": "esbenp.prettier-vscode"
  },
  "[typescriptreact]": {
    "editor.defaultFormatter": "esbenp.prettier-vscode"
  }
}

Dengan konfigurasi di atas:

  1. Menekan tombol Simpan (Save) otomatis memformat berkas dengan Prettier.
  2. Lint-error yang bisa diperbaiki secara otomatis (seperti import yang tidak terurut atau variabel tidak terpakai yang bisa dihilangkan) akan diperbaiki oleh ESLint saat proses simpan.

© 2026 Bit Group Asia. All rights reserved.

ArchitectureSecurityGuidelines