Level 3 · Sistem yang Saling Bergantung
Sesi 26: Ketika Semua Mencoba Lagi: Retry Storms, Jitter, & Backoff
Bagaimana jika niat baik aplikasi di 10.000 smartphone untuk "mencoba kembali" secara serentak justru membunuh server yang baru saja selesai restart, mengubah pemadaman 10 detik menjadi bencana 3 jam?
1. Bayangkan Jika
Sebuah pintu gerbang stadion konser musik tertutup mendadak karena engselnya macet. Di depan pintu, ada 10.000 orang antre. Petugas berhasil memperbaiki engsel dalam 10 detik.
Tepat saat pintu dibuka sedikit, seluruh 10.000 orang secara sinkron menabrakkan tubuh mereka ke pintu pada detik yang sama (Retry serentak). Pintu hancur berkeping-keping, petugas terinjak, dan konser batal total.
Jika 10.000 orang tersebut mundur beberapa langkah, menunggu dengan jeda waktu acak yang bervariasi (Exponential Backoff with Full Jitter), arus masuk akan mengalir tenang tanpa merusak pintu gerbang.
2. Apa yang Sebenarnya Terjadi
Ketika server atau koneksi downstream mengalami gangguan sementara (transient error):
-
Blind Immediate Retry (Retry Buta Tanpa Jeda): - 5.000 klien gagal request pada detik ke-0. - Tanpa jeda, 5.000 klien mengirim retry serentak pada detik ke-0.1. - Beban server yang awalnya 5.000 QPS seketika melonjak menjadi 10.000 QPS (2x lipat) tepat saat server sedang megap-megap. - Inilah Retry Storm (Badai Retry).
-
Jebakan Fixed Delay (Semua Retry di Detik yang Sama): - Klien diberi delay tetap 1 detik. - Hasilnya: lonjakan beban berpindah dari detik ke-0 ke detik ke-1 secara harmonik (waves of traffic spikes). Server tetap dihantam gelombang kejut periodik.
3. Tiga Senjata Peredam Badai
-
Exponential Backoff: - Tingkatkan waktu tunggu secara eksponensial untuk setiap kegagalan beruntun:
\text{Wait Time} = \text{Base} \times 2^{\text{attempt}}- Percobaan 1: 100 ms \rightarrow Percobaan 2: 200 ms \rightarrow Percobaan 3: 400 ms \rightarrow Percobaan 4: 800 ms. -
Full Jitter (Pemberian Derau Acak): - Eksponensial saja masih bisa memicu gelombang harmonik jika ribuan klien gagal di detik yang sama. - Solusi Amazon AWS: Tambahkan komponen acak murni (Full Jitter):
\text{Sleep} = \text{random}(0, \text{Base} \times 2^{\text{attempt}})- Trafik retry yang padat seketika terurai menyebar rata secara merata di sepanjang garis waktu (flat smooth distribution). -
Idempotency Key & Retry Budget: - Idempotency Key (
X-Idempotency-Key: uuid): Menjamin bahwa jika server menerima request pembayaran yang sama 3 kali karena jaringan timeout di sisi klien, kartu kredit pengguna hanya dipotong 1 kali. - Retry Budget (Envoy / Finagle): Batasi bahwa maksimal hanya 10% dari total trafik yang boleh berupa retry request. Jika kuota retry habis, request langsung fail-fast.
4. Nama Resminya
- Retry Storm: Lonjakan trafik destruktif yang disebabkan oleh upaya pengulangan request gagal yang tersinkronisasi.
- Exponential Backoff: Algoritma penundaan di mana durasi tunggu digandakan setiap kali terjadi kegagalan.
- Jitter: Variasi acak yang disuntikkan ke dalam durasi backoff untuk memecah resonansi sinkronisasi trafik.
- Idempotency: Properti operasi di mana mengeksekusi request berkali-kali menghasilkan efek akhir yang sama persis seperti mengeksekusinya satu kali.
- Retry Budget: Mekanisme pembatasan rasio pengulangan pada layer proxy jaringan.
5. Di Dunia Kita
- AWS SDK / Google Cloud Client: Secara default menyertakan Exponential Backoff dengan Full Jitter pada semua panggilan API.
- Stripe / Midtrans Payment API: Mewajibkan header
Idempotency-Keypada endpoint/chargesuntuk mencegah tagihan ganda saat terjadi retry otomatis.
6. Lensa Performance Tester
Metrik dan pengujian krusial:
1. Traffic Spike vs Smooth Distribution: Simulasikan 5.000 klien gagal serentak dengan Fixed Delay vs Full Jitter. Bandingkan grafik QPS puncak (peak surge).
2. Double Charge Prevention: Kirim 10 request bayar paralel dengan Idempotency-Key yang identik. Pastikan hanya ada 1 record mutasi bank dan 9 respons lainnya me-replay hasil transaksi pertama.
3. Retry Budget Depletion: Uji perilaku Envoy saat hilir mati total: verifikasi bahwa rasio retry berhenti di batas 10% dan tidak melipatgandakan trafik masuk.
7. Pertanyaan untuk Ronde Berikutnya
Ketika data transaksi terus masuk dan layanan harus berkomunikasi tanpa saling menunggu secara langsung, arsitektur apa yang digunakan untuk menampung jutaan event secara aman di latar belakang?
Jawabannya ada di Sesi 27: Menampung Beban Tanpa Menunggu: Message Queue, Backpressure, & DLQ.