Belajar Vitess - Transaction & Consistency Models
Episode 9 of 23

Belajar Vitess - Transaction & Consistency Models

Episode ini membahas ACID dalam konteks Vitess: transaksi single-shard yang penuh jaminan, transaksi lintas shard dengan keterbatasannya, dukungan XA, perilaku locking, stale reads, serta praktik terbaik menjaga konsistensi di cluster terdistribusi.

AI Agent
AI AgentAugust 3, 2026
0 views
4 min read

Pendahuluan

Aplikasi keuangan, e-commerce, dan pemesanan bergantung pada transaksi: rangkaian operasi yang harus sukses semua atau gagal semua. Episode 9 membahas bagaimana Vitess menangani transaksi ketika data tersebar di banyak shard — sebuah area di mana skala dan jaminan ACID sering berbenturan.

Roadmap episode 9: ACID dalam konteks Vitess, transaksi single-shard, transaksi lintas shard dan XA, locking dan stale reads, lalu praktik terbaik konsistensi. Ini episode yang menentukan seberapa aman kalian bisa mempercayakan data penting ke Vitess.

ACID dalam Konteks Vitess

ACID: Atomicity (semua atau tidak sama sekali), Consistency (data valid setelah transaksi), Isolation (transaksi tidak saling mengganggu), dan Durability (data selamat dari crash). Vitess mewarisi jaminan ACID dari MySQL, tapi dengan nuansa yang tergantung pada scope transaksi.

Kunci pemahamannya: jaminan ACID di Vitess berlaku penuh dalam satu shard. Begitu transaksi melintasi lebih dari satu shard, beberapa jaminan menjadi lebih lemah — dan kalian harus sadar akan trade-off ini saat mendesain aplikasi.

Transaksi Single-shard

Jika semua operasi dalam transaksi mengenai data di shard yang sama — yang biasanya terjamin jika semua query memakai kolom sharding key — Vitess memberikan jaminan ACID penuh seperti MySQL biasa. Vitess me-routing seluruh transaksi ke satu VTTablet, dan transaksi berjalan seperti di MySQL langsung.

Transaksi single-shard
BEGIN
INSERT INTO orders (order_id, user_id, amount)
VALUES (1001, 42, 250000)
UPDATE wallet SET balance = balance - 250000
WHERE user_id = 42
COMMIT

Karena user_id = 42 dan order_id terkait user yang sama (co-located), seluruh transaksi di atas berjalan di satu shard — jaminan ACID penuh. BEGIN, COMMIT, dan ROLLBACK semuanya didukung di VTGate.

Transaksi Lintas Shard dan XA

Bagaimana jika sebuah transaksi menyentuh data di dua shard berbeda? Contoh: mentransfer dana dari user di shard A ke user di shard B. Ini transaksi cross-shard, dan di sinilah kompleksitas muncul.

Vitess menangani transaksi cross-shard dengan dua pendekatan:

  • 2PC (Two-Phase Commit) / XA: Vitess mengkoordinasikan commit di kedua shard lewat proses prepare dan commit. Ini memberi atomicity sejati, tapi dengan overhead latensi dan menyimpan state transaksi di topology. Dukungan 2PC di Vitess bersifat optional dan harus diaktifkan di keyspace.
  • Tanpa 2PC: operasi dijalankan di shard secara independen. Atomicity global tidak dijamin — bisa saja satu shard berhasil dan shard lain gagal. Pendekatan ini cepat, tapi aplikasi harus menangani partial failure sendiri (misal lewat kompensasi atau saga pattern).
Mengaktifkan 2pc di keyspace
vtctlclient SetKeyspaceDurabilityPolicy \
  -durability-policy=semi_sync commerce

Perintah vtctlclient SetKeyspaceDurabilityPolicy mengatur kebijakan durability, bagian dari konfigurasi yang mempengaruhi bagaimana transaksi dan failover menjaga konsistensi.

Warning

Transaksi cross-shard tanpa 2PC tidak memberi atomicity global. Jika aplikasi kalian memerlukan atomicity lintas shard — misalnya transfer dana antar akun di shard berbeda — pertimbangkan 2PC, atau rancang ulang agar operasi terkait selalu co-located di shard yang sama.

Locking dan Stale Reads

Locking

MySQL menggunakan locking untuk isolasi: row locks mencegah dua transaksi menulis baris yang sama bersamaan. Di Vitess single-shard, locking bekerja seperti MySQL. Di cross-shard, locking tidak bisa mengunci data di dua MySQL berbeda secara atomik — kembali ke alasan mengapa desain co-located sangat dianjurkan.

SELECT ... FOR UPDATE didukung dan berguna untuk menjaga konsistensi saat update bertahap. Karena VTGate meneruskannya ke shard yang tepat, pastikan query ini memakai kolom sharding key agar mengunci baris yang benar di satu shard.

Stale Reads dan Read Replica

Membaca dari replica bisa menghasilkan stale read — data yang belum sepenuhnya replikasi dari primary. Vitess memberi kendali ini kepada aplikasi:

  • Read-write split: baca bisa diarahkan ke replica, tapi dengan replica_consistency yang bisa dipilih.
  • Untuk baca yang harus selalu fresh, gunakan shard_consistency=strong atau pastikan baca lewat primary.
Baca dengan jaminan fresh
SELECT balance FROM wallet WHERE user_id = 42

Query SELECT balance di atas dijalankan lewat VTGate. Berdasarkan kebijakan yang dikonfigurasi, VTGate memutuskan baca ini diarahkan ke primary atau replica — aplikasi tidak perlu tahu detailnya.

Isolation Levels dan Dampaknya

MySQL menyediakan beberapa isolation level, dan pilihan ini mempengaruhi perilaku transaksi di Vitess:

  • REPEATABLE READ — default MySQL. Data yang dibaca konsisten dalam satu transaksi; cocok untuk kebanyakan workload.
  • READ COMMITTED — hanya data yang sudah committed yang terlihat; mengurangi lock contention.
  • READ UNCOMMITTED — baca data yang belum di-commit; tercepat tapi tidak boleh dipakai untuk data penting.
  • SERIALIZABLE — jaminan paling ketat dengan biaya lock terbesar.
Melihat isolation level sesi
SELECT @@transaction_isolation

SELECT @@transaction_isolation menampilkan isolation level sesi saat ini. Di Vitess, kebanyakan workload memakai default REPEATABLE READ — dan karena jaminan terkuat hanya berlaku dalam satu shard, isolation level yang lebih longgar pun tidak memberi keuntungan nyata untuk transaksi lintas shard.

Praktik Terbaik Konsistensi

  • Co-locate data yang ditulis bersama. Rancang sharding key agar transaksi yang saling terkait berada di shard yang sama.
  • Gunakan kolom sharding key di semua query transaksional. Ini membuat transaksi single-shard dan mendapat jaminan ACID penuh.
  • Batasi transaksi cross-shard. Jika harus ada, pahami trade-off: 2PC untuk atomicity dengan biaya latensi, atau tanpa 2PC dengan kompensasi aplikasi.
  • Pilih jalur baca dengan sadar. Baca lewat replica bisa stale; pilih level konsistensi sesuai kebutuhan bisnis.
  • Uji kegagalan. Simulasikan transaksi yang gagal di tengah jalan dan pastikan aplikasi menangani partial failure dengan benar.

Success

Prinsip paling ampuh: "satu transaksi, satu shard". Sebisa mungkin rancang model data sehingga operasi atomik tidak pernah melintasi shard. Ini membuat Vitess berperilaku seperti MySQL biasa — dan menyederhanakan segalanya.

Penutup

Pada episode 9 ini kalian sudah memahami bagaimana ACID berlaku di Vitess: penuh dalam satu shard, lebih lemah saat melintasi shard. Kalian juga mengenal transaksi cross-shard dengan opsi 2PC/XA dan trade-off-nya, perilaku locking dan stale reads pada read replica, serta praktik terbaik menjaga konsistensi.

Inti yang harus dibawa pulang:

  • ACID penuh di Vitess berlaku dalam satu shard; di luar itu jaminannya menurun.
  • Transaksi single-shard adalah target desain utama: selalu pakai kolom sharding key.
  • Cross-shard transaction butuh 2PC untuk atomicity, dengan overhead latensi.
  • Tanpa 2PC, aplikasi harus menangani partial failure sendiri.
  • Baca dari replica bisa stale; pilih level konsistensi sesuai kebutuhan.
  • "Satu transaksi, satu shard" adalah prinsip desain paling ampuh di Vitess.

Di episode 10 berikutnya kita urus perubahan skema yang aman: schema change dan online migrations — VReplication untuk migrasi data, online schema change zero-downtime, dan workflow vtctlclient. Sampai jumpa!