Topik ini membahas rebalancing pada consumer group, yaitu perhitungan ulang penugasan partisi ketika komposisi group berubah. Pembahasannya mencakup pemicu rebalancing, biaya penghentian konsumsi pada protokol lama, protokol kooperatif yang memangkas pekerjaan ulang, sampai pergantian anggota yang diuji langsung pada broker. Setelah membacanya, durasi dan dampak rebalancing dapat dijelaskan dari protokol yang dipilih beserta konfigurasi waktu pada klien.
Pemicu rebalancing#
Rebalancing dipicu oleh perubahan keanggotaan group, perubahan langganan topic, dan perubahan jumlah partisi topic yang dilanggani. Anggota baru yang bergabung, anggota yang keluar dengan bersih, dan anggota yang dinyatakan mati semuanya mengubah daftar keanggotaan, sehingga group coordinator memicu perhitungan penugasan ulang. Penambahan partisi mengubah himpunan yang harus dibagikan kepada anggota, dan perubahan itu pun memicu rebalancing meskipun jumlah anggotanya tetap.
Anggota dinyatakan mati melalui dua jalur waktu. Jalur pertama adalah heartbeat, yaitu sinyal hidup berkala yang dikirim thread latar belakang ke coordinator. Apabila sinyal itu tidak lagi tiba sebelum session timeout berakhir, yaitu 45000 milidetik pada nilai default session.timeout.ms, coordinator melepas anggota tersebut lalu memicu rebalancing. Jalur kedua adalah max.poll.interval.ms, yaitu 300000 milidetik pada nilai defaultnya, yang membatasi jeda antar panggilan poll(), dan anggota yang melewati batas itu dianggap gagal sehingga partisinya dibagikan kembali.
Konfigurasi waktu yang terlalu agresif memunculkan rebalancing tanpa kegagalan sungguhan. Aplikasi dengan pemrosesan panjang yang jarang memanggil poll() perlu menaikkan max.poll.interval.ms, sedangkan session.timeout.ms yang diperpendek terlalu jauh melepas anggota yang hanya tertahan jaringan. Nilai default aman untuk kebanyakan beban kerja, dan penyesuaiannya dilakukan setelah pola pemrosesan terukur, bukan sebagai langkah pertama saat konsumsi tampak lambat.
Biaya stop-the-world#
Protokol penugasan lama, yaitu protokol eager, menuntut agar seluruh anggota melepas semua partisinya sebelum penugasan baru disusun. Konsumsi berhenti total sejak permintaan join group dikirim sampai penugasan baru diterima, keadaan yang dikenal sebagai stop-the-world. Semakin banyak partisi dan anggota yang dilibatkan, semakin lama jeda itu, karena penugasan disusun oleh anggota pemimpin lalu disebar kembali ke seluruh anggota.
Biaya jeda itu lebih dari sekadar waktu tunggu group. Pemrosesan yang sudah setengah selesai harus dihentikan lalu dilanjutkan pada anggota lain, sehingga pekerjaan yang sama berisiko diulang dari awal. Aplikasi di hilir menanggung aliran yang berhenti mendadak lalu mengejar pesan yang menumpuk, dan lag yang terbentuk selama rebalancing baru tertutup setelah konsumsi berjalan kembali. Group besar yang rebalancing-nya sering terpicu menghabiskan sebagian kapasitasnya untuk pekerjaan penugasan, bukan untuk pemrosesan pesan.
Durasi jeda paling terlihat saat anggota bergabung dalam jumlah besar, karena coordinator menunggu seluruh anggota mendaftar ulang sebelum penugasan disusun. Besaran biaya inilah yang membuat protokol penugasan dianggap keputusan arsitektur, bukan sekadar detail konfigurasi.
Protokol kooperatif dan KIP-848#
Protokol cooperative rebalancing mengubah langkah yang paling mahal pada protokol eager, yaitu pelepasan seluruh partisi. Anggota hanya melepas partisi yang memang harus berpindah pemilik, sedangkan partisi yang tidak berpindah terus dikonsumsi selama rebalancing berlangsung. Penugasan diselesaikan dalam dua gelombang kecil, sehingga penghentian total digantikan oleh pekerjaan ulang yang jauh lebih sedikit. Pemilihan protokol dilakukan lewat konfigurasi partition.assignment.strategy, dengan nilai CooperativeStickyAssignor untuk mengaktifkannya, sedangkan strategi sticky mempertahankan pembagian lama selama keanggotaan tidak berubah.
Kafka 4.x membawa protokol consumer baru yang dirancang dalam KIP-848 dan diaktifkan dengan konfigurasi group.protocol=consumer. Pada protokol ini perhitungan penugasan berpindah ke sisi broker, sehingga rebalancing berlangsung bertahap tanpa penghentian total dan tanpa penugasan yang disusun oleh anggota pemimpin. Statusnya mencapai generally available (GA) pada Kafka 4.0, sedangkan nilai default group.protocol masih classic pada Kafka 4.4. Konfigurasi klien milik protokol classic seperti session.timeout.ms dan heartbeat.interval.ms tidak berlaku pada protokol baru, karena batas waktu sesinya dikelola broker lewat group.consumer.session.timeout.ms.
Diagram berikut merangkum alur protokol eager dari pemicu sampai konsumsi kembali berjalan, yaitu urutan yang membuat seluruh group berhenti sementara pada setiap rebalancing.
Pergantian anggota pada CLI#
Pemicu rebalancing yang paling sederhana adalah anggota yang keluar lalu digantikan anggota baru, dan peristiwa itu dapat diperagakan dengan consumer console. Demo menggunakan topic tetap m1-rebal-demo dengan satu partisi bersama group m1-grup-rebal, keduanya dihapus lebih dulu agar jumlah pesan dan posisi group selalu sama pada setiap eksekusi.
(
cd /home/kal/my-project/kafka-runtime/kafka
bin/kafka-consumer-groups.sh --bootstrap-server localhost:9092 --delete --group m1-grup-rebal >/dev/null 2>/dev/null
bin/kafka-topics.sh --bootstrap-server localhost:9092 --delete --if-exists --topic m1-rebal-demo 2>/dev/null
sleep 2
bin/kafka-topics.sh --bootstrap-server localhost:9092 --create --topic m1-rebal-demo --partitions 1
)Created topic m1-rebal-demo.Blok berikut mengisi log dengan tiga pesan lalu menjalankan anggota pertama group m1-grup-rebal dengan kuota dua pesan. Anggota itu bergabung, membaca dua pesan pertama, meng-commit posisi 2, kemudian keluar dengan bersih setelah kuotanya terpenuhi. Peristiwa masuk dan keluar itu masing-masing memicu satu rebalancing pada group yang sama.
(
cd /home/kal/my-project/kafka-runtime/kafka
printf "satu\ndua\ntiga\n" | bin/kafka-console-producer.sh --bootstrap-server localhost:9092 --topic m1-rebal-demo 2>/dev/null
bin/kafka-console-consumer.sh --bootstrap-server localhost:9092 --topic m1-rebal-demo --group m1-grup-rebal --from-beginning --max-messages 2 2>/dev/null
)satu
duaAnggota kedua bergabung pada group yang sama tanpa opsi --from-beginning, sehingga ia membaca dari committed offset 2 dan hanya menerima pesan ketiga. Tabel deskripsi di akhir blok menunjukkan CURRENT-OFFSET 3 dengan LAG 0, yang berarti konsumsi berlanjut tanpa duplikasi dan tanpa pesan yang terlewat di antara pergantian anggota.
(
cd /home/kal/my-project/kafka-runtime/kafka
bin/kafka-console-consumer.sh --bootstrap-server localhost:9092 --topic m1-rebal-demo --group m1-grup-rebal --max-messages 1 2>/dev/null
bin/kafka-consumer-groups.sh --bootstrap-server localhost:9092 --describe --group m1-grup-rebal 2>/dev/null
)tiga
GROUP TOPIC PARTITION CURRENT-OFFSET LOG-END-OFFSET LAG CONSUMER-ID HOST CLIENT-ID
m1-grup-rebal m1-rebal-demo 0 3 3 0 - - -Keluaran ini memperlihatkan sisi rebalancing yang tidak terlihat secara langsung, yaitu posisi 2 yang tersimpan oleh anggota pertama menjadi titik mulai anggota kedua. Pada cluster nyata, pergantian anggota seperti ini memicu rebalancing yang durasinya ditentukan protokol yang digunakan, sedangkan urutan konsumsinya tetap sama. Group dengan protokol kooperatif menyelesaikan pergantian yang sama tanpa menghentikan partisi yang pemiliknya tidak berpindah.
Kesalahan umum#
- Pemrosesan satu pesan berlangsung lebih lama dari
max.poll.interval.ms, sehingga anggota dianggap gagal dan partisinya berpindah di tengah pekerjaan. Rebalancing berulang setiap kali beban memanjat. Naikkanmax.poll.interval.mssesuai durasi pemrosesan terlama, atau kecilkanmax.poll.recordsagar setiap perulanganpoll()lebih pendek. - Anggota keluar tanpa menutup consumer dengan rapi, sehingga coordinator menunggu
session.timeout.msberlalu sebelum memicu rebalancing dan jeda konsumsi memanjang. Tutup consumer denganclose()saat aplikasi berhenti, atau panggilwakeup()dari thread lain untuk menghentikan perulanganpoll()secara bersih. - Pemrosesan dilakukan lama setelah
poll()kembali, kemudian offset tertinggi di-commit, sedangkan rebalancing memindahkan partisi sebelum pemrosesan selesai sehingga pesan diproses ulang atau terlewat. Commit posisi tepat setelah batch selesai dan tangani duplikasi pada sisi pemroses.
Ringkasan#
- Rebalancing dipicu oleh anggota yang masuk, keluar, atau dianggap mati lewat heartbeat,
session.timeout.ms, danmax.poll.interval.ms. - Protokol eager melepas seluruh partisi sehingga konsumsi berhenti total selama rebalancing berlangsung.
- Protokol kooperatif hanya melepas partisi yang berpindah pemilik, dan KIP-848 memindahkan perhitungan penugasan ke broker lewat
group.protocol=consumer. - Anggota baru melanjutkan konsumsi dari committed offset, sehingga pergantian anggota tidak mengulang pesan yang sudah ter-commit.
Referensi#
- Consumer configs — Apache Software Foundation
— konfigurasi
session.timeout.ms,heartbeat.interval.ms,max.poll.interval.ms, dangroup.protocolyang digunakan pada pembahasan. - KIP-848: The Next Generation of the Consumer Rebalance Protocol — Apache Software Foundation — proposal protokol rebalancing baru yang mencapai GA pada Kafka 4.0.
- Apache Kafka documentation — Apache Software Foundation — dokumentasi utama yang menjelaskan cara coordinator menangani keanggotaan group.