Semester 3 · 4 SKS · 200 menit · Project 05 — ERD

Relationship & ERD

Pertemuan 4 menghasilkan lima tabel yang berdiri sendiri. Sekarang kita sambungkan tabel-tabel tersebut: keterkaitan antarentitas, kardinalitas relasi, serta mekanisme database dalam menjaga integritas referensial.

Konsep → Kasus NyataPrediksi → CodingJalankan → Analisis

Target Pertemuan

Di akhir kelas, Anda mampu merancang hubungan antar-data dan menggambarkannya sebagai ERD yang memuat entity, atribut, primary key, foreign key, dan kardinalitasnya.

PK → FK
Memahami kunci asing (foreign key) sebagai penghubung dari satu tabel ke baris tabel lain.
Kardinalitas
Membedakan relasi 1:1, 1:N, dan N:M melalui analisis perbandingan jumlah keterhubungan.
ERD
Menggambar relasi secara manual sebagai bekal CRUD (P6) dan blueprint (P7).
Aturan kelas tetap sama: AI boleh membantu membuat contoh, mencari dokumentasi, debugging, dan merapikan SQL. Anda tetap harus mampu menjelaskan setiap garis pada ERD Anda: tabel apa tersambung, lewat kolom apa, dan mengapa kardinalitasnya begitu. Paper First, AI Later.

Contoh SQL dapat disalin dan dimodifikasi. Setiap garis pada ERD wajib memiliki dasar argumentasi yang jelas.

Pertanyaan Pembuka

Nota laundry bernomor 7 tercatat atas nama pelanggan nomor 99 — padahal pelanggan nomor 99 tidak ada. Komponen manakah yang perlu diperbaiki: prosedur pencatatan kasir, format nota, atau mekanisme validasi pada sistem? Tuliskan analisis Anda di kertas sebelum membuka laptop.

1. Dari Pertemuan 4 ke Pertemuan 5

Pertemuan 4 menghasilkan tabel-tabel yang berdiri sendiri. Permasalahannya: tabel transaksi mencatat id_pelanggan tanpa mekanisme yang memastikan bahwa data pelanggan yang dirujuk benar-benar tersedia — sebagaimana ilustrasi nota bernomor pelanggan 99 di atas.

Tabel sendiri-sendiri
P4
→
Sambung dengan FK
P5 hari ini
→
Operasi data aman
CRUD · P6
→
Blueprint V1
P7
Batas materi hari ini (sesuai kerangka): PK, FK, 1:1, 1:N, N:M, redundansi, normalisasi dasar, ERD. Operasi INSERT/SELECT/UPDATE/DELETE secara penuh baru di Pertemuan 6 — hari ini SQL hanya untuk membuktikan relasi bekerja.

2. Primary Key Bertemu Foreign Key

Primary key (PK) berfungsi sebagai penanda identitas yang bersifat unik pada setiap baris. Foreign key (FK) berfungsi sebagai penunjuk dari satu tabel ke kunci utama pada tabel lain sebagai bukti keterhubungan.

Cara membaca satu FK

KomponenContoh laundry
Tabel anak (memiliki FK)transaksi
Kolom FKtransaksi.id_pelanggan
Menunjuk kepelanggan.id_pelanggan (PK)
Artinya“Transaksi ini milik pelanggan itu.”

FK tidak menciptakan data baru — ia menghubungkan dua baris yang sudah ada.

Ketentuan foreign key

  • FK wajib menunjuk ke baris yang ada — merujuk pada data pelanggan yang tidak tersedia akan ditolak oleh sistem.
  • Tipe data FK harus sama dengan PK yang ditunjuk (INT → INT).
  • Penghapusan baris pada tabel induk yang masih memiliki baris terkait pada tabel anak dapat ditolak atau dibatasi — mekanisme ini menjamin integritas referensial dan mencegah terbentuknya baris tanpa referensi yang valid (orphan record).
  • Di MySQL/MariaDB, tabel berelasi harus memakai mesin penyimpanan InnoDB.
Prediksi: apa yang terjadi apabila pengguna memasukkan data transaksi dengan id_pelanggan = 99 padahal tabel pelanggan hanya berisi 1–3? (Jawaban: ditolak dengan error 1452 — buktikan di Praktik.)

3. Kardinalitas Relasi

Kardinalitas dianalisis melalui dua pertanyaan: “satu baris pada tabel A berhubungan dengan berapa baris pada tabel B?” dan sebaliknya.

1 : 1 — Satu berbanding satu

Satu baris pada tabel A berhubungan tepat dengan satu baris pada tabel B. Contoh: satu pengguna → satu profil kasir; satu kos → satu kontrak aktif.

Jarang dipakai; biasanya untuk memisahkan data sensitif atau opsional.

1 : N — Satu berbanding banyak

Satu baris pada tabel induk berhubungan dengan banyak baris pada tabel anak; satu baris pada tabel anak hanya merujuk pada satu baris tabel induk. Pola paling umum. Contoh: satu pelanggan → banyak transaksi.

Kunci asing selalu ditempatkan pada sisi N (banyak).

N : M — Banyak berbanding banyak

Banyak baris pada tabel A berhubungan dengan banyak baris pada tabel B. Contoh: mahasiswa ↔ mata kuliah; obat ↔ resep.

Wajib diuraikan melalui tabel perantara (junction table) — mis. tabel ambil / peminjaman.

Satu pola pada berbagai jenis usaha

Kerangka memakai contoh kampus (dosen–matakuliah, mahasiswa–matakuliah). Pola yang sama dapat ditemukan pada berbagai jenis usaha. Pahami polanya, bukan sekadar menghafalkan contohnya:

PolaLaundryKampusBooking LapanganPerpustakaanBengkel
1 : NPelanggan → TransaksiDosen → Matakuliah (yang diajar)Pelanggan → BookingAnggota → PeminjamanKendaraan → Servis
1 : NTransaksi → PembayaranJurusan → MahasiswaLapangan → BookingBuku → PeminjamanMekanik → Servis
N : M (via perantara)— (laundry murni 1:N)Mahasiswa ↔ Matakuliah via ambilTim ↔ Turnamen via peserta_turnamenAnggota ↔ Buku via peminjamanSparepart ↔ Servis via pakai_sparepart
Cek pemahaman lisan: sistem kos — Pemilik : Kamar : Penyewa : Pembayaran. Manakah yang berelasi 1:N? Apakah terdapat relasi N:M? (Contoh jawaban: satu kamar memiliki banyak riwayat sewa; satu penyewa → banyak pembayaran; kamar ↔ fasilitas via tabel perantara.)

4. Redundansi & Normalisasi Dasar

Sebelum menyusun ERD final, struktur data perlu dirapikan terlebih dahulu: data yang sama tidak seyogianya disimpan secara berulang pada banyak lokasi.

Bentuk belum ternormalisasi dan bentuk ternormalisasi

Belum ternormalisasi: tabel penjualan turut menyimpan nama_pelanggan, alamat_pelanggan, nama_produk, harga_produk — nama “Andi” tercatat sebanyak 20 kali; apabila nomor telepon berubah, 20 baris tersebut harus diperbarui satu per satu.

Ternormalisasi: tabel penjualan dan detail_penjualan hanya menyimpan id_pelanggan dan id_produk; nama dan alamat hanya tersimpan pada tabel induk. Perubahan dilakukan satu kali dan berlaku untuk seluruh referensi.

Normalisasi dasar (tiga kaidah)

  1. Satu sel = satu nilai. Kolom layanan tidak seyogianya diisi dengan beberapa nilai sekaligus seperti “cuci, setrika, antar” — nilai tersebut perlu dipisahkan menjadi baris atau tabel tersendiri.
  2. Kolom non-kunci tergantung penuh pada PK. Nama pelanggan bergantung pada id_pelanggan, bukan pada id_transaksi — oleh karena itu atribut tersebut ditempatkan pada tabel pelanggan.
  3. Tidak ada kolom yang tergantung pada kolom non-kunci. total_harga tidak perlu disimpan secara redundan apabila nilainya selalu dapat dihitung dari berat dikalikan tarif (atau diberi penanda yang jelas sebagai hasil perhitungan).
Kesalahan umum: menyusun satu tabel besar yang memuat seluruh kolom dengan alasan kepraktisan. Pendekatan tersebut menyulitkan pemeliharaan: pembaruan menjadi tidak konsisten dan duplikasi data tidak terkendali.

5. Membaca ERD — Komponen yang Wajib Lengkap

ERD ERD pada Project Book wajib memuat: entitas, atribut, kunci utama, kunci asing, serta relasi (jenis dan arahnya).

SimbolArtiCara baca
KotakEntity / tabelpelanggan, transaksi
Garis + label 1:NRelasi satu-ke-banyak“Satu pelanggan memiliki banyak transaksi.”
Ujung bercabang (notasi crow's foot)Sisi “banyak” (N)Notasi cabang selalu terletak pada sisi tabel anak (sisi N, tempat kunci asing berada).
Kotak di tengah dua tabelTabel perantara N:Mpeminjaman menghubungkan anggota ↔ buku.
Setiap garis relasi wajib dapat dinyatakan dalam kalimat: “Satu ___ memiliki banyak ___; satu ___ hanya merujuk pada satu ___.” Apabila kalimat tersebut tidak dapat disusun, rancangan relasi perlu ditinjau kembali.

6. Praktik — Membangun Database Penjualan dari Awal

Alur Paper First, AI Later: susun ERD pada kertas terlebih dahulu (kotak entitas, garis relasi, dan label kardinalitas), kemudian tulis SQL dan jalankan. Praktik ini memakai database baru penjualan_db yang dibangun dari awal, sehingga tidak menyentuh database laundry_db dari Pertemuan 4.

Diagram — ERD Penjualan (1:N dan N:M yang Diuraikan)

Notasi cabang selalu terletak pada sisi tabel anak. Tabel detail_penjualan merupakan tabel perantara yang menguraikan relasi N:M antara penjualan dan produk menjadi dua relasi 1:N.

ERD penjualan: pelanggan, penjualan, produk, detail penjualan, pembayaran Pelanggan satu ke banyak penjualan. Penjualan satu ke banyak pembayaran. Produk dan penjualan masing-masing satu ke banyak detail penjualan sebagai tabel perantara. Kunci asing ditempatkan pada sisi banyak (N). pelangganPK id_pelanggannama · no_hp penjualanPK id_penjualanFK id_pelanggan pembayaranPK id_pembayaranFK id_penjualan produkPK id_produknama · harga detail_penjualanPK id_detailFK id_penjualanFK id_produk 1:N 1:N 1:N 1:N FK terletak pada sisi N Cara membaca: satu pelanggan memiliki banyak penjualan;satu penjualan memuat banyak produk melalui detail_penjualan.

Siapkan di XAMPP

  1. Buka XAMPP Control Panel, pastikan Apache dan MySQL running (phpMyAdmin butuh keduanya).
  2. Buka http://localhost/phpmyadmin. Mini coding 1 membuat database baru penjualan_db, sehingga database laundry_db dari Pertemuan 4 tidak tersentuh.
  3. Buka tab SQL, tempelkan mini coding 1, kemudian klik Go/Kirim — jalankan satu kali. Lanjutkan ke mini coding 2 untuk tahap pembuktian.
Seluruh tabel memakai InnoDB agar kunci asing aktif — blok SQL di bawah telah mengaturnya. Perintah memakai IF NOT EXISTS sehingga aman dijalankan ulang tanpa menghapus data.
Mini coding 1 — bangun database dan 5 tabel dari awal
CREATE DATABASE IF NOT EXISTS penjualan_db
  CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci;

USE penjualan_db;

-- 1. Pelanggan (tabel induk)
CREATE TABLE IF NOT EXISTS pelanggan (
  id_pelanggan INT AUTO_INCREMENT PRIMARY KEY,
  nama VARCHAR(100) NOT NULL,
  no_hp VARCHAR(20),
  alamat TEXT
) ENGINE=InnoDB;

-- 2. Produk / barang dagangan (tabel induk)
CREATE TABLE IF NOT EXISTS produk (
  id_produk INT AUTO_INCREMENT PRIMARY KEY,
  nama_produk VARCHAR(100) NOT NULL,
  harga INT NOT NULL,
  stok INT NOT NULL DEFAULT 0
) ENGINE=InnoDB;

-- 3. Penjualan (1 pelanggan : N penjualan)
CREATE TABLE IF NOT EXISTS penjualan (
  id_penjualan INT AUTO_INCREMENT PRIMARY KEY,
  id_pelanggan INT NOT NULL,
  tanggal DATE NOT NULL,
  total INT NOT NULL DEFAULT 0,
  CONSTRAINT fk_jual_pelanggan
    FOREIGN KEY (id_pelanggan) REFERENCES pelanggan (id_pelanggan)
) ENGINE=InnoDB;

-- 4. Detail penjualan : tabel perantara N:M (penjualan ↔ produk)
CREATE TABLE IF NOT EXISTS detail_penjualan (
  id_detail INT AUTO_INCREMENT PRIMARY KEY,
  id_penjualan INT NOT NULL,
  id_produk INT NOT NULL,
  jumlah INT NOT NULL,
  subtotal INT NOT NULL,
  CONSTRAINT fk_detail_jual
    FOREIGN KEY (id_penjualan) REFERENCES penjualan (id_penjualan),
  CONSTRAINT fk_detail_produk
    FOREIGN KEY (id_produk) REFERENCES produk (id_produk)
) ENGINE=InnoDB;

-- 5. Pembayaran (1 penjualan : N pembayaran)
CREATE TABLE IF NOT EXISTS pembayaran (
  id_pembayaran INT AUTO_INCREMENT PRIMARY KEY,
  id_penjualan INT NOT NULL,
  tanggal_bayar DATETIME DEFAULT CURRENT_TIMESTAMP,
  jumlah_bayar INT NOT NULL,
  metode ENUM('tunai','transfer','qris') NOT NULL DEFAULT 'tunai',
  CONSTRAINT fk_bayar_jual
    FOREIGN KEY (id_penjualan) REFERENCES penjualan (id_penjualan)
) ENGINE=InnoDB;
Mini coding 2 — isi contoh dan pembuktian relasi
USE penjualan_db;

-- Data contoh: 2 pelanggan dan 3 produk.
INSERT INTO pelanggan (nama, no_hp, alamat) VALUES
  ('Andi', '081234567890', 'Jl. Merpati No. 10'),
  ('Sinta', '082133344455', 'Jl. Anggrek No. 8');

INSERT INTO produk (nama_produk, harga, stok) VALUES
  ('Buku Tulis', 12000, 50),
  ('Pulpen', 5000, 100),
  ('Tas Ransel', 150000, 10);

-- A. PEMBUKTIAN 1: merujuk pada pelanggan yang tidak tersedia — WAJIB ditolak (galat 1452).
-- Sampaikan prediksi terlebih dahulu, kemudian jalankan. Sesuaikan nilai 9999 apabila diperlukan.
INSERT INTO penjualan (id_pelanggan, tanggal, total)
VALUES (9999, '2026-10-01', 17000);

-- B. PEMBUKTIAN 2: data yang konsisten — WAJIB diterima.
-- Satu penjualan berisi dua produk melalui tabel perantara. ID yang tersedia dapat diperiksa melalui tab Browse.
INSERT INTO penjualan (id_pelanggan, tanggal, total)
VALUES (1, '2026-10-01', 17000);

INSERT INTO detail_penjualan (id_penjualan, id_produk, jumlah, subtotal) VALUES
  (1, 1, 1, 12000),
  (1, 2, 1, 5000);

INSERT INTO pembayaran (id_penjualan, jumlah_bayar, metode)
VALUES (1, 17000, 'tunai');

-- C. PEMBUKTIAN 3: membaca nota lengkap lintas tabel (pengantar CRUD pada Pertemuan 6).
SELECT j.id_penjualan AS nota, p.nama AS pelanggan,
       pr.nama_produk AS barang, d.jumlah, d.subtotal
FROM penjualan AS j
JOIN pelanggan AS p ON p.id_pelanggan = j.id_pelanggan
JOIN detail_penjualan AS d ON d.id_penjualan = j.id_penjualan
JOIN produk AS pr ON pr.id_produk = d.id_produk
ORDER BY j.id_penjualan DESC, d.id_detail ASC
LIMIT 10;

Alur pada kode

CREATE DATABASE + TABLE
Membuat wadah penjualan_db beserta lima tabel sekaligus dengan kunci utama masing-masing.
CONSTRAINT … FOREIGN KEY
Menetapkan aturan bahwa suatu kolom merujuk pada kunci utama tabel lain sehingga integritasnya ditegakkan oleh sistem database; tabel perantara memuat dua kunci asing.
Pengujian penolakan dan JOIN
Data yang tidak valid wajib gagal tersimpan; data yang valid wajib diterima; JOIN membuktikan bahwa nota kini dapat dibaca lintas tabel sebagai satu kesatuan.

7. Jalankan, Uji, dan Amati

Pengujian relasi tidak cukup sekadar menampilkan pesan keberhasilan. Sampaikan prediksi terlebih dahulu, kemudian jalankan perintah dan catat hasilnya.

Kasus ujiCaraHasil yang seharusnya
FK menolak referensi yang tidak validINSERT penjualan dengan id_pelanggan = 9999Galat 1452 Cannot add or update a child row — penjualan tanpa pelanggan yang sah tidak dapat tersimpan.
FK menolak penghapusan data indukDELETE FROM pelanggan WHERE id_pelanggan = 1; yang masih memiliki data penjualan terkaitDitolak selama baris terkait masih tersedia — mekanisme pengaman berfungsi.
Ketidaksesuaian tipe dataKunci asing bertipe INT merujuk pada kunci utama bertipe VARCHAR (uji pada tabel latihan)Galat 150 Foreign key constraint is incorrectly formed.
JOIN membaca notaQuery C di mini coding 2Muncul nama pelanggan + nama barang, bukan angka ID saja.
Relasi terdaftarphpMyAdmin → tabel penjualan → Structure → Relation viewTercatat 1 kunci asing; pada tabel detail_penjualan tercatat 2 kunci asing.
Apabila terjadi galat: No database selected berarti lupa baris USE penjualan_db;. Galat 150 menunjukkan tipe kolom tidak sama. Apabila mini coding 2 dijalankan dua kali, baris contoh akan ganda — kosongkan tabel terlebih dahulu bila ingin mengulang dari awal.

8. Mini Challenge

  1. Gambarkan relasi N:M pada sistem kampus (mahasiswa ↔ mata kuliah), kemudian uraikan menjadi dua relasi 1:N melalui tabel ambil(id_ambil PK, id_mahasiswa FK, id_mk FK). Tuliskan kalimat pembacaan relasi tersebut dalam dua arah.
  2. Pada sistem pilihan Anda: identifikasikan satu hubungan yang awalnya tampak sebagai N:M, kemudian tentukan tabel perantaranya beserta kunci utama dan kunci asingnya.
  3. Lakukan satu kali pelanggaran batasan kunci asing (memasukkan baris anak tanpa baris induk yang sesuai) dan dokumentasikan galat 1452 yang muncul. Analisis: komponen manakah yang melakukan penolakan — aplikasi PHP atau sistem database?
  4. Identifikasikan satu kolom yang terduplikasi pada rancangan Anda (misalnya nama yang tersimpan pada dua tabel). Pindahkan ke tabel induk dan gantikan dengan kunci asing pada tabel anak. Analisis perubahan yang terjadi pada query JOIN.
Challenge menjelaskan ERD: tunjuk satu garis relasi, sebutkan kedua tabel beserta kolom penghubungnya, bacakan kalimat “satu … memiliki banyak …”, dan tunjukkan letak kunci asingnya.

9. Hubungkan dengan Project Semester — Project 05 ERD

Susun ERD sistem pilihan Anda secara manual — hasil ini menjadi dasar penyusunan CRUD Matrix (P6) dan Blueprint V1 (P7).

Booking lapangan
Pelanggan 1:N Booking; Lapangan 1:N Booking; Booking 1:N Pembayaran. Tim ↔ Turnamen via perantara bila ada.
Perpustakaan
Anggota 1:N Peminjaman; Buku 1:N Peminjaman (Peminjaman = perantara Anggota ↔ Buku). Denda 1:1 dengan Peminjaman telat.
Bengkel / Toko / Kos
Kendaraan 1:N Servis; Produk 1:N Detail Transaksi; Kamar 1:N Riwayat Sewa. Sparepart ↔ Servis via pakai_sparepart.

Hindari penyalinan ERD contoh tanpa adaptasi. Setiap garis wajib dapat dibaca dalam dua arah dan setiap kunci asing wajib ditempatkan pada sisi N. Contoh sistem kampus tetap dapat digunakan sebagai pembanding, bukan sebagai satu-satunya acuan.

10. Tugas Project Book — Minggu 5

  1. Tetap gunakan sistem project semester yang sama.
  2. Gambarkan ERD secara manual: kotak entitas beserta atributnya, serta tandai kunci utama (garis bawah / *) dan kunci asing (tanda #).
  3. Berikan label kardinalitas pada setiap garis (1:1 / 1:N / N:M yang telah diuraikan) beserta nomor aturan kunci asingnya.
  4. Wujudkan minimal 3 relasi di phpMyAdmin (ALTER TABLE … FOREIGN KEY) dan lampirkan bukti (tangkapan layar Relation view / ekspor SQL).
  5. Susun analisis tertulis: untuk setiap relasi cantumkan kalimat pembacaan dua arah, alasan penetapan kardinalitas, serta respons penolakan dari sistem database. Pindai atau foto dengan jelas dan unggah ke Google Drive sesuai arahan dosen.
Format analisis Project Book:
Tabel anak → kolom kunci asing → kunci utama tabel yang dirujuk → kardinalitas beserta kalimat pembacaan → bukti pengujian (diterima/ditolak) → argumentasi.

11. Quis Pertemuan 5

  1. Jelaskan perbedaan kunci utama dan kunci asing. Pada sisi manakah (1 atau N) kunci asing selalu ditempatkan?
  2. Jelaskan 1:1, 1:N, N:M — masing-masing satu contoh dari usaha berbeda (bukan ketiganya dari kampus).
  3. Mengapa relasi N:M wajib diuraikan dengan tabel perantara? Jelaskan kunci utama dan kunci asing pada tabel perantara tersebut.
  4. Apa itu redundansi? Mengapa penyimpanan nama pelanggan pada tabel transaksi menimbulkan risiko inkonsistensi?
  5. Sebutkan tiga kaidah normalisasi dasar sebagaimana diuraikan dalam materi ini beserta contoh penerapannya.
  6. Jelaskan makna galat 1452. Komponen manakah yang melakukan penolakan — aplikasi PHP atau sistem database — dan mengapa hal tersebut menunjukkan integritas data terjaga?
  7. Bacakan satu garis pada ERD penjualan dalam dua arah dengan kalimat lengkap.

Quis/aktivitas mengikuti aturan kelas dan arahan dosen. Pastikan ERD yang dikumpulkan dapat Anda pertanggungjawabkan untuk setiap garis relasinya.

12. Ringkasan

PK
identitas baris
→
FK
penunjuk relasi
→
Kardinalitas
1:1 · 1:N · N:M
→
ERD
gambar + aturan

Kunci utama menetapkan identitas. Kunci asing menjaga keterhubungan. ERD menyajikan keduanya secara visual dan teruji.

Pertemuan 6 memanfaatkan relasi ini sebagai dasar operasi CRUD. Simpan Project Book, ERD manual, dan berkas SQL Anda.

Glosarium

Istilah bertanda garis putus-putus dapat diarahkan kursor atau difokuskan untuk menampilkan definisi singkat.

Primary KeyKolom identitas baris: unik, wajib isi, stabil.
Foreign KeyKolom penunjuk ke PK tabel lain; penghubung relasi.
KardinalitasUkuran hubungan: 1:1, 1:N, atau N:M.
One-to-ManySatu baris induk memiliki banyak baris anak; pola paling umum.
Many-to-ManyBanyak lawan banyak; wajib dipecah via tabel perantara.
Tabel PerantaraTabel junction pemecah N:M, berisi dua FK (mis. peminjaman).
RedundansiData sama tersimpan berulang; sumber inkonsistensi.
NormalisasiAturan merapikan tabel agar tiap fakta tersimpan sekali.
ERDEntity-Relationship Diagram: gambar entity, kunci, dan relasi.
InnoDBEngine MySQL/MariaDB yang mendukung foreign key.