~/VibeHandbook
PDF Gratis

Bab 14 · 03

Dasar-Dasar Desain Skema

Skema adalah cetak biru datamu: tabel apa saja yang ada, kolom apa yang dimilikinya, dan bagaimana mereka saling berhubungan. Desain skema yang baik sebagian besar adalah akal sehat ditambah beberapa kebiasaan.

  • Satu tabel per "hal." Users, posts, orders — masing-masing punya tabelnya sendiri.
  • Setiap baris butuh ID unik (primary key).
  • Hubungkan tabel dengan foreign key, bukan dengan menyalin data ke sana kemari.
  • Pilih tipe yang jujur. Uang adalah decimal, bukan float. Tanggal adalah timestamp, bukan teks.
  • Jangan duplikasi. Kalau email seorang pengguna tersimpan di lima tabel, cepat atau lambat kamu akan punya lima email yang berbeda-beda.

Berikut skema sederhana untuk sebuah blog, jenis yang akan dibuatkan AI untukmu:

CREATE TABLE users (
    id          UUID PRIMARY KEY DEFAULT gen_random_uuid(),
    email       TEXT NOT NULL UNIQUE,
    created_at  TIMESTAMPTZ NOT NULL DEFAULT now()
);

CREATE TABLE posts (
    id          UUID PRIMARY KEY DEFAULT gen_random_uuid(),
    author_id   UUID NOT NULL REFERENCES users(id),
    title       TEXT NOT NULL,
    body        TEXT NOT NULL,
    published   BOOLEAN NOT NULL DEFAULT false,
    created_at  TIMESTAMPTZ NOT NULL DEFAULT now()
);

CREATE INDEX idx_posts_author ON posts(author_id);

Baris author_id ... REFERENCES users(id) itu adalah foreign key-nya. Ia menghubungkan setiap post kembali ke tepat satu pengguna yang benar-benar ada, sehingga basis data itu sendiri menolak menyimpan post tanpa penulis yang valid:

   users                          posts
   ┌─────────────┐                ┌─────────────┐
   │ id  (PK) ◀──┼────────────────┤ author_id   │  (FK → users.id)
   │ email       │   one user      │ id  (PK)    │
   │ created_at  │   has many      │ title       │
   └─────────────┘   posts         │ body        │
                                   │ published   │
        1  ────────────────────▶  *└─────────────┘
       (one)                    (many)

Perhatikan REFERENCES (foreign key yang mengikat sebuah post ke pengguna yang benar-benar ada) serta constraint NOT NULL dan UNIQUE. Ini adalah pagar pengaman yang ditegakkan basis data untukmu, sehingga data buruk tidak bisa menyelinap masuk bahkan ketika kodemu punya bug.

Satu constraint yang layak ditambahkan secara sengaja adalah apa yang terjadi saat induknya (parent) hilang. Secara default, menghapus pengguna yang post-nya masih merujuk padanya akan gagal — dan itu sering kali memang yang kamu inginkan. Tapi kamu bisa membuatnya eksplisit: REFERENCES users(id) ON DELETE CASCADE akan menghapus post-nya juga, sementara ON DELETE RESTRICT memblokir penghapusan tersebut. Memilih dengan sengaja lebih baik daripada menemukan perilaku default lewat cara yang menyakitkan di production. Insting "biarkan basis data melindungimu" yang sama juga berlaku untuk constraint CHECK (CHECK (price >= 0)) — ia menolak data yang tidak masuk akal langsung dari sumbernya, alih-alih mempercayai setiap jalur kode untuk memvalidasi.

Mau versi offline?

Unduh seluruh buku sebagai PDF atau EPUB — gratis.