Topik wawancara representatif

Wawancara Data Engineering: Bagaimana Cara Mendiagnosis dan Memperbaiki Hot Kafka Partition?

DataSulit
Tim Redaksi Offer.ccDipublikasikan Diperbarui

Pertanyaan

Sebuah topik Kafka memiliki 24 partisi dan menerima 120.000 record per detik pada puncaknya. Satu tenant menghasilkan 45% dari lalu lintas, dan produsen mempartisi berdasarkan tenant_id, sehingga satu partisi terus tertinggal sementara sebagian besar konsumen lainnya menganggur. Satu konsumen saat ini dapat memproses 8.000 record per detik, pengurutan hanya diperlukan dalam satu pesanan, dan Anda tidak dapat menambahkan partisi selama insiden berlangsung. Bagaimana cara Anda mendiagnosis, memitigasi, dan memperbaiki masalah ini secara permanen? Cakup offset, rebalance, efek duplikat, dan validasi migrasi.

Pertanyaan dan Kapan Ini Berlaku

Sebuah topik Kafka memiliki 24 partisi dan menerima 120.000 record per detik pada saat beban puncak. Satu tenant menghasilkan 45% dari total traffic, dan producer mempartisi berdasarkan tenant_id, sehingga satu partisi terus mengakumulasi lag sementara sebagian besar consumer lainnya menganggur. Satu consumer dapat mempertahankan pemrosesan 8.000 record per detik dengan handler saat ini. Kebutuhan bisnis hanya mensyaratkan keterurutan (ordering) dalam cakupan satu order_id, bukan di seluruh event dari tenant tersebut, dan penambahan partisi tidak dapat dilakukan selama insiden berlangsung.

Jelaskan bagaimana Anda akan membuktikan bahwa key skew, bukan kegagalan consumer, broker, atau downstream, yang menyebabkan gejala tersebut. Kemudian jelaskan bagaimana Anda akan mengurangi pertumbuhan backlog hari ini, mendesain ulang partition key dan proses migrasi, serta meng-commit offset secara aman setelah menambahkan pemrosesan asinkron. Akhiri dengan metrik dan pengujian kegagalan yang menunjukkan keberhasilan perbaikan tersebut.

Ini adalah pertanyaan pemecahan masalah data engineering dan platform streaming. Panduan wawancara Kafka publik saat ini menyajikan kombinasi yang pada dasarnya sama: satu partisi yang panas (hot partition), consumer-nya tertinggal, consumer lain menganggur, producer berbasis key, dan tidak ada perubahan jumlah partisi secara langsung. Pertanyaan ini meminta kandidat untuk menghubungkan pemartisian producer, paralelisme consumer, dan keterurutan data. Dokumentasi Apache Kafka menyatakan bahwa producer default memilih partisi dengan melakukan hashing pada key yang ada. Pemartisian semantik menjaga lokalitas dan urutan di dalam partisi yang dipilih, tetapi juga memusatkan traffic dari key tersebut di sana. Panduan Kafka dari Huawei Cloud juga menyatakan bahwa satu partisi hanya dapat dikonsumsi oleh satu consumer pada satu waktu dan penambahan partisi untuk sementara bukanlah cara cepat untuk membersihkan backlog partisi yang ada.

Throughput, pembagian traffic, kapasitas consumer, dan cakupan keterurutan dalam pertanyaan ini adalah asumsi wawancara, bukan angka produksi yang diatribusikan ke perusahaan tertentu.

Apa yang Dievaluasi oleh Pewawancara

Sinyal pertama adalah apakah Anda dapat beralih dari metrik agregat ke bukti di tingkat partisi. Lag di seluruh topik, rata-rata CPU consumer, dan jumlah consumer semuanya dapat menyembunyikan satu hot partition. Jawaban yang kuat menyelaraskan produce rate, consume rate, kemiringan lag (lag slope), leader broker, distribusi key, dan waktu pemrosesan downstream dari setiap partisi pada timeline yang sama. Hal ini memisahkan skew pada producer dari handler yang lambat, rebalance yang berulang, atau tekanan sumber daya broker.

Sinyal kedua adalah apakah Anda mengukur insiden tersebut secara kuantitatif:

text
120,000 × 45% = 54,000 records/second

Jika consumer yang ditugaskan ke partisi tersebut hanya dapat memproses 8.000 record per detik, backlog akan bertambah sebesar:

text
54,000 - 8,000 = 46,000 records/second
46,000 × 600 = 27,600,000 records in 10 minutes

Perhitungan tersebut menjelaskan mengapa menambahkan consumer biasa tidak mengubah batas atas (ceiling) partisi ini dan mengapa mengubah ambang batas peringatan tidak memitigasi insiden tersebut.

Sinyal ketiga adalah apakah Anda mengidentifikasi invarian keterurutan yang sebenarnya. Key saat ini memperluas domain keterurutan ke seluruh tenant, padahal bisnis hanya memerlukan urutan di dalam satu pesanan. Mengubah key menjadi order_id meningkatkan kardinalitas dan mendistribusikan pesanan baru, tetapi hanya jika migrasi mencegah satu pesanan melintasi dua partisi atau topik.

Sinyal keempat adalah kebenaran offset (offset correctness). Begitu record dari satu partisi dijalankan dalam worker pool, urutan penyelesaian dapat berbeda dari urutan offset. Jika offset 105 selesai sementara 104 masih berjalan, melakukan commit hingga 105 dapat melewatkan 104 setelah terjadi crash. Desain yang kuat melacak offset selesai yang bersebelahan tertinggi (highest contiguous completed offset) dan membuat efek downstream menjadi idempoten karena record yang sudah selesai tetapi belum di-commit dapat diputar ulang (replayed).

Sinyal terakhir adalah apakah Anda menyatakan batasan mutlaknya. Lebih banyak partisi menciptakan lebih banyak slot paralel, tetapi tidak memecah entitas raksasa yang tetap terikat pada satu key. Menambahkan lebih banyak consumer dalam consumer group tradisional tidak memungkinkan dua consumer memiliki partisi yang sama secara bersamaan. Jika satu pesanan saja melebihi kapasitas aman satu partisi dan harus tetap terurut secara ketat, tuas yang tersisa adalah mengoptimalkan jalur serial, melakukan throttling, atau mendefinisikan ulang urutan bisnis yang independen.

Pertanyaan untuk Diklarifikasi Sebelum Menjawab

  • Apakah pengurutan diperlukan per tenant, per pesanan, atau untuk stream event yang lebih kecil? Jika urutan di seluruh tenant adalah wajib, pemisahan tenant tidak valid. Jika urutan di tingkat pesanan sudah cukup, order_id adalah batas partisi yang lebih akurat.
  • Apakah 45% menggambarkan jumlah record, byte, atau biaya pemrosesan? Record yang besar atau operasi penulisan downstream yang mahal dapat menciptakan cost skew meskipun jumlah record tampak seimbang. Periksa record, byte, dan waktu handler.
  • Apakah produce rate meningkat, atau kapasitas konsumsi menurun? Angka konstan 54.000 record per detik dibandingkan kapasitas 8.000 record menunjukkan adanya key skew dan kapasitas per-key yang tidak mencukupi. Jika input tidak berubah tetapi konsumsi turun dari 8.000 menjadi 2.000, selidiki sistem downstream, garbage collection, jaringan, disk, dan rebalance terlebih dahulu.
  • Ke mana consumer menulis data? Pipeline Kafka-to-Kafka dapat meng-commit output dan input offset secara atomik dengan transaksi Kafka. Database, object store, atau API eksternal biasanya memerlukan pemrosesan at-least-once ditambah business idempotency key atau topic-partition-offset.
  • Berapa lama suatu pesanan dapat tetap aktif? Pesanan berumur pendek dapat tetap berada di rute lama hingga selesai sementara pesanan baru menggunakan rute baru. Pesanan berumur panjang memerlukan barrier, sequence, atau routing state yang eksplisit.
  • Bisakah respons insiden membatasi (throttle) atau menurunkan kualitas (degrade) traffic? Kuota tenant, penundaan event analitik yang tidak kritis, atau penggabungan (coalescing) pembaruan status dapat mengurangi input lebih cepat daripada migrasi kode dan partisi.
  • Apakah consumer melebihi max.poll.interval.ms? Jika pekerjaan berat memblokir poll thread, rebalance akan memperparah lag. Pisahkan polling dari pemrosesan dan batasi in-flight work sebelum sekadar menaikkan nilai timeout.

Kerangka Jawaban 30 Detik

"Saya akan memecah lag agregat menjadi produce rate, consume rate, dan lag slope per partisi, lalu menyelaraskannya dengan frekuensi key, byte, waktu handler, log rebalance, dan metrik leader broker. Tenant yang panas menghasilkan 54.000 record per detik sementara satu consumer menangani 8.000, sehingga backlog bertambah sekitar 46.000 per detik; menambahkan consumer biasa tidak dapat mempercepat partisi tersebut. Untuk saat ini, saya akan melakukan throttle atau degrade pada tenant yang panas, mengisolasi partisi tersebut pada instance khusus, dan memanfaatkan batas keterurutan yang sebenarnya dengan menserialisasikan setiap pesanan sambil memproses pesanan yang berbeda secara bersamaan (konkuren). Saya hanya akan meng-commit highest contiguous completed offset dan menggunakan penulisan downstream yang idempoten. Untuk jangka panjang, pesanan baru akan dipindahkan ke topik baru dengan key order_id, sementara pesanan yang ada tetap berada di rute lama hingga selesai. Saya akan memvalidasi lag slope tingkat partisi, end-to-end p99, duplikasi, dan pelanggaran urutan di bawah beban yang timpang, crash pada consumer, dan rebalance."

Jawaban Mendalam Langkah demi Langkah

Langkah 1: Buktikan lapisan mana yang menciptakan hotspot

Gunakan satu jendela waktu beban puncak dan selaraskan:

  1. produce record per detik, byte per detik, dan pertumbuhan high-watermark berdasarkan partisi;
  2. consume record per detik, committed offset, dan lag slope berdasarkan partisi;
  3. frekuensi key, byte, dan estimasi distribusi biaya pemrosesan;
  4. CPU, jaringan, disk wait, dan latensi permintaan pada leader broker dari partisi yang panas;
  5. interval polling, ukuran batch, latensi handler, garbage collection, error, dan log rebalance untuk consumer yang ditugaskan;
  6. latensi atau throttling yang berkorelasi dengan partisi pada database downstream, sistem penyimpanan, atau API.

Aturan keputusan mengikuti angka-angka tersebut. Partisi yang panas menerima sekitar 54.000 record per detik. Sebanyak 23 partisi lainnya berbagi sisa 66.000 record, dengan rata-rata sekitar 2.870 record per detik jika sisanya terdistribusi secara seragam. Consumer dengan kapasitas 8.000 record memiliki kapasitas berlebih pada partisi biasa tetapi tidak dapat mengimbangi input yang panas. Hal ini sepenuhnya menjelaskan mengapa satu partisi terus bertambah lag-nya sementara ada kapasitas menganggur di tempat lain. Jika input partisi panas normal sementara konsumsi menurun sejalan dengan latensi downstream, desain key belum terbukti sebagai akar penyebabnya.

Periksa juga penempatan broker. Partisi yang leader-nya berada di broker yang kelebihan beban dapat mengalami proses produce dan fetching yang lebih lambat. Memindahkan leadership atau menyeimbangkan ulang replika dapat menghilangkan hambatan penempatan tersebut, tetapi tidak mengubah fakta bahwa satu tenant_id masih memetakan ke satu partisi.

Langkah 2: Kurangi laju backlog sebelum mencoba mengurasnya

Tujuan insiden yang pertama adalah:

text
hot-partition input rate ≤ hot-partition safe processing rate

Tuas tercepat sering kali adalah penerimaan (admission). Terapkan kuota eksplisit pada tenant yang panas, tunda event analitik yang dapat direkonstruksi, gabungkan (coalesce) pembaruan yang hanya mementingkan status terbaru, atau tempatkan pekerjaan non-kritis pada jalur degradasi yang ditentukan. Setiap tindakan memerlukan semantik kehilangan, penundaan, dan replay yang jelas. Menghapus record secara diam-diam bukanlah strategi throttling.

Di sisi consumer, jendela pemeliharaan yang terkontrol dapat menghentikan grup yang ada dan menggantinya dengan penugasan eksplisit yang eksklusif dan tidak tumpang tindih: satu instance yang diprovisi secara memadai hanya memiliki partisi yang panas, dan instance yang tersisa memiliki partisi lainnya. Memulai consumer group biasa kedua bukanlah bantuan; grup tersebut akan secara independen mengonsumsi seluruh topik dan menduplikasi efek bisnis. Isolasi mencegah partisi panas membuat partisi biasa kelaparan (starvation) pada proses yang sama, meskipun itu tidak menaikkan handler serial asli di atas 8.000 record per detik.

Karena bisnis hanya memerlukan keterurutan di dalam satu pesanan, consumer yang menangani partisi panas dapat mendistribusikan data berdasarkan order_id: satu antrean serial per pesanan aktif dan worker pool terbatas untuk berbagai pesanan yang berbeda. Pool tersebut harus memiliki batas in-flight. Jika sudah penuh, jeda (pause) partisi atau kurangi jumlah yang dilepaskan ke worker agar Kafka lag tidak menjadi memori proses yang tak terbatas. Loop polling harus tetap responsif; jika tidak, melebihi max.poll.interval.ms akan memicu rebalance dan menambah jeda lainnya.

Langkah 3: Commit batas penyelesaian yang bersebelahan (contiguous completion watermark)

Konkurensi intra-partisi mengubah urutan penyelesaian, tetapi tidak boleh mengubah urutan commit. Pertahankan status ini untuk setiap partisi:

text
nextCommitOffset = smallest unfinished offset
completed = offsets that finished but still have a gap before them

onComplete(offset):
  add offset to completed
  while completed contains nextCommitOffset:
    remove nextCommitOffset from completed
    increment nextCommitOffset
  commit nextCommitOffset

Kafka meng-commit posisi berikutnya yang akan dibaca. Oleh karena itu, hanya setelah 104, 105, dan 106 semuanya selesai, posisi yang di-commit dapat maju ke 107. Jika 105 selesai sementara 104 mencoba ulang (retry), titik commit tetap di 104. Crash sebelum commit berikutnya akan memutar ulang beberapa record yang sudah selesai, sehingga operasi penulisan database harus menggunakan event_id atau business-unique key lainnya untuk upsert yang idempoten. Jika tidak ada business key, topic-partition-offset dapat mengidentifikasi record sumber.

Jangan menggambarkan offset commit dan efek samping eksternal sebagai sesuatu yang secara alami atomik. Aplikasi Kafka-to-Kafka dapat menempatkan output record dan consumed offset dalam satu transaksi Kafka. Dengan database eksternal, kontrak yang lebih umum adalah konsumsi at-least-once ditambah penulisan idempoten, atau transaksi database yang berisi record deduplikasi dan mutasi bisnis.

Langkah 4: Sesuaikan cakupan partisi dengan domain keterurutan yang sebenarnya

Kapasitas rata-rata dari 24 partisi belum tentu tidak mencukupi. Jika 8.000 record per detik adalah batas maksimum aman yang terukur dan pemanfaatan yang direncanakan dibatasi pada 70%, kapasitas yang direncanakan per partisi adalah 5.600:

text
120,000 ÷ 5,600 ≈ 21.4

Dengan distribusi yang merata, 24 partisi mencakup asumsi puncak dengan sedikit ruang luang (headroom). Kegagalan berasal dari penempatan 45% traffic di balik satu key dengan kardinalitas rendah, bukan dari jumlah partisi agregat. Key yang tahan lama harus mewakili domain keterurutan terkecil yang diperlukan, memiliki kardinalitas yang cukup, dan tetap terdistribusi secara terprediksi pada beban puncak. Di sini, order_id adalah pilihan yang alami. Pengkodean stabil dari (tenant_id, order_id) juga dimungkinkan jika lokalitas tenant memiliki nilai operasional yang nyata.

Salting terkontrol hanya valid jika record di dalam key asli boleh diubah urutannya atau tahap downstream dapat memulihkan urutan. Melakukan random salting pada satu pesanan melanggar invarian pertanyaan ini karena pesanan tersebut dapat tiba secara bersamaan dari beberapa partisi. Jika satu pesanan saja melebihi kapasitas partisi tunggal, kardinalitas key yang lebih besar tidak akan membantu; optimalkan atau throttle jalur serial pesanan tersebut, atau desain ulang protokol bisnis menjadi urutan yang secara eksplisit independen.

Langkah 5: Migrasi dengan versioned routing

Menambahkan partisi ke topik yang ada dan langsung mengubah key menimbulkan dua risiko. Pemetaan hash default dapat memindahkan key yang ada ketika jumlah partisi berubah. Event untuk satu pesanan juga dapat mendarat di partisi yang berbeda sebelum dan sesudah cutover, sementara Kafka tidak menjamin keterurutan lintas-partisi.

Desain yang lebih aman adalah membuat topik baru yang dipartisi berdasarkan order_id dan membuat versi pada perutean producer:

  • pesanan yang dibuat setelah cutover menggunakan topik baru;
  • pesanan yang sudah ada tetap berada di topik lama dan key lama hingga ditutup;
  • setiap producer menggunakan status perutean pesanan yang sama alih-alih membandingkan jam lokalnya dengan waktu cutover;
  • consumer membaca kedua rute, tetapi satu pesanan hanya menjadi milik satu rute aktif pada saat tertentu;
  • topik lama dipensiunkan setelah pesanan lama habis (drained) dan persyaratan retensi terpenuhi.

Jika pesanan tidak selesai secara alami, buat barrier migrasi per pesanan: jeda event baru untuk pesanan tersebut, tunggu hingga rute lama mencapai urutan atau offset akhir yang tercatat, ubah versi perutean, dan lanjutkan. Alternatif tanpa jeda dapat menyertakan nomor urut monoton dan menggabungkan kedua rute di downstream, tetapi itu menimbulkan buffering, timeout, dan pemulihan celah (gap recovery). Hal ini hanya dibenarkan jika kebutuhan bisnis sebanding dengan kompleksitas tersebut.

Langkah 6: Validasi dengan traffic yang timpang dan pengujian kegagalan

Throughput agregat bukanlah bukti yang cukup. Uji setidaknya:

  • distribusi di mana satu tenant menghasilkan 45% traffic dan distribusi pesanan menyerupai beban puncak nyata;
  • input, konsumsi, lag slope, dan lag maksimum berdasarkan partisi;
  • end-to-end p50, p95, dan p99 ditambah estimasi waktu pengurasan (drain time);
  • jumlah in-flight worker, umur task tertua, retry, dan dead letter;
  • efek duplikat, pelanggaran urutan per pesanan, dan konflik idempotensi;
  • crash pada consumer saat offset yang selesai memiliki celah (gap);
  • apakah pemrosesan yang lama memicu rebalance dan berapa lama waktu pemulihannya;
  • apakah suatu pesanan hanya muncul di satu rute pada batas topik lama/baru.

Kondisi kelulusan mencakup perilaku yang berkelanjutan: lag slope partisi panas tidak lagi positif pada beban puncak yang stabil; crash dapat memutar ulang pekerjaan tetapi tidak boleh menghilangkan efek bisnis; tidak ada pesanan yang teramati di luar urutan; pesanan baru terdistribusi di seluruh partisi; dan pesanan lama terkuras sesuai jadwal. Jika throughput agregat meningkat sementara satu pesanan besar berulang kali menciptakan hotspot, domain keterurutan atau masalah penerimaan bisnis masih belum terselesaikan.

Contoh Jawaban Berkualitas Tinggi

"Saya tidak akan memulai dengan menambahkan consumer karena pertanyaan ini sudah memberi tahu kita bahwa satu partisi tertinggal sementara consumer di tempat lain menganggur. Pertama, saya akan membuktikan adanya skew menggunakan record per detik, byte per detik, lag slope, dan frekuensi key per partisi, sekaligus mengesampingkan leader broker, rebalance, dan latensi downstream.

Tenant yang panas menghasilkan 54.000 record per detik. Satu consumer partisi memproses 8.000, sehingga lag tumbuh sekitar 46.000 record per detik, atau 27,6 juta dalam 10 menit. Jika 55% lainnya tersebar secara kasar di 23 partisi, masing-masing rata-rata menerima sekitar 2.870 record per detik. Hal itu menjelaskan defisit pada consumer yang panas dan adanya kapasitas cadangan di tempat lain. Dalam consumer group tradisional, satu partisi menjadi milik satu consumer pada satu waktu, sehingga instance biasa yang lebih banyak tidak akan mempercepatnya.

Hari ini, saya pertama-tama akan mengurangi laju input dengan kuota tenant yang terdokumentasi dan memindahkan event yang toleran terhadap penundaan atau dapat digabungkan ke jalur degradasi. Dalam jendela pemeliharaan terkontrol, saya akan mengisolasi partisi yang panas pada instance khusus agar tidak membuat partisi biasa kekurangan sumber daya. Karena hanya keterurutan per pesanan yang penting, saya akan mendistribusikan data berdasarkan order_id ke bounded pool: serial dalam satu pesanan, konkuren untuk pesanan yang berbeda. Saya tidak akan meng-commit task mana pun yang selesai paling cepat. Saya akan melacak highest contiguous completed offset dan berhenti di celah (gap) mana pun. Crash dapat memutar ulang record yang sudah selesai tetapi belum di-commit, sehingga sink menggunakan event_id atau business-unique key untuk idempotensi.

Untuk jangka panjang, menambah partisi bukanlah perbaikan yang menyeluruh. Pada utilisasi terencana 70%, setiap partisi berkapasitas 8.000 record menyumbang sekitar 5.600 record per detik, sehingga 24 partisi yang terbebani secara merata dapat mencakup asumsi beban puncak 120.000 record. Masalahnya adalah tenant_id mematok 45% beban ke satu partisi. Saya akan membuat topik baru dengan key order_id. Pesanan baru setelah cutover menggunakannya, sementara pesanan lama yang aktif tetap berada di rute lama sampai selesai. Status perutean bersama memastikan bahwa satu pesanan tidak pernah berada di kedua topik sekaligus.

Sebelum rollout, saya akan memutar ulang 45% tenant skew yang sama dan memeriksa throughput per partisi, lag slope, end-to-end p99, duplikasi, dan pelanggaran urutan. Saya akan menghentikan consumer secara paksa (crash) saat offset selesai di luar urutan dan memverifikasi bahwa restart hanya menyebabkan replay yang idempoten, memicu rebalance dan mengukur pemulihannya, serta memverifikasi bahwa setiap pesanan di batas rute hanya muncul di satu topik. Jika satu pesanan itu sendiri melebihi kapasitas partisi tunggal, saya akan menyatakan batasan mutlaknya: baik menambah consumer maupun menambah partisi tidak akan menyelesaikannya tanpa mengoptimalkan, membatasi (throttle), atau mengubah model pengurutan pesanan tersebut."

Kesalahan Umum

  • Hanya melihat lag di seluruh topik → Nilai rata-rata menyembunyikan laju input dan konsumsi dari satu partisi → Gambarkan grafik record, byte, lag, dan distribusi key per partisi.
  • Menambahkan consumer setiap kali lag meningkat → Satu partisi dalam grup tradisional hanya dimiliki oleh satu consumer pada satu waktu → Bandingkan jumlah partisi, penugasan, dan kapasitas per partisi terlebih dahulu.
  • Langsung menambahkan partisi → Backlog yang ada tidak terdistribusi ulang secara otomatis, dan pemetaan key default dapat berubah → Hentikan pertumbuhan backlog terlebih dahulu, lalu gunakan topik berversi dan batas migrasi.
  • Memberi salt acak pada key yang panas → Satu pesanan dapat melintasi partisi dan tiba tidak berurutan → Gunakan salt hanya jika perubahan urutan diperbolehkan; gunakan order_id untuk cakupan keterurutan sebenarnya pada kasus ini.
  • Meng-commit offset segera setelah worker-nya selesai → Offset lebih rendah yang belum selesai dapat terlewatkan setelah terjadi crash → Commit hanya batas penyelesaian yang bersebelahan (contiguous completion watermark).
  • Menyebut commit offset sebagai pemrosesan exactly-once → Mutasi database eksternal dan offset Kafka biasanya tidak berada dalam satu transaksi → Nyatakan batasan at-least-once, idempotensi, dan transaksi.
  • Memulai consumer group kedua untuk membantu → Grup kedua membaca salinan lengkapnya sendiri dan menduplikasi efek bisnis → Gunakan penugasan eksplisit eksklusif atau desain ulang pemrosesan yang terkontrol.
  • Hanya menguji traffic yang seragam → Nilai rata-rata yang lolos uji tidak membuktikan bahwa hot key telah hilang → Putar ulang skew yang realistis dan periksa partisi maksimum, bukan hanya rata-ratanya.
  • Mengabaikan batas entitas tunggal → Satu entitas yang terurut ketat tidak dapat diparalelkan di seluruh partisi secara cuma-cuma → Nyatakan trade-off yang sulit antara keterurutan, throttling, dan pemrosesan serial.

Pertanyaan Lanjutan dan Tanggapannya

Lanjutan 1: Mengapa tidak langsung menambah jumlah partisi dari 24 menjadi 48?

Partisi baru menciptakan slot paralel untuk masa depan, tetapi tidak membagi backlog yang sudah tersimpan di partisi lama, juga tidak membuat satu tenant_id memetakan ke beberapa partisi. Dengan hashing key default, mengubah jumlah partisi juga dapat memetakan ulang key yang ada dan menempatkan satu pesanan pada partisi yang berbeda selama proses cutover. Perbaiki domain keterurutan dan migrasi terlebih dahulu, lalu gunakan uji beban yang timpang untuk memutuskan apakah penambahan partisi agregat memang diperlukan.

Lanjutan 2: Bagaimana cara mencegah memori tak terbatas setelah menambahkan konkurensi intra-partisi?

Tetapkan batas maksimum record in-flight dan jendela offset uncommitted maksimum per partisi. Ketika salah satu batas tercapai, jeda partisi tersebut atau kurangi pelepasan record ke worker pool sambil menjaga polling tetap terpisah dari pemrosesan berat. Lacak umur offset tertua yang belum selesai. Jika satu pesanan tetap terblokir, isolasi, coba lagi, atau rutekan untuk intervensi daripada membiarkan setiap offset berikutnya mengonsumsi memori tanpa batas.

Lanjutan 3: Bagaimana jika database downstream tidak mendukung upsert yang idempoten?

Sisipkan record deduplikasi dan lakukan mutasi bisnis dalam satu transaksi database. Gunakan event_id atau topic-partition-offset bisnis sebagai unique key; konflik keunikan berarti event tersebut telah diterapkan. Untuk API eksternal non-transaksional, gunakan idempotency key, outbox, atau status operasi yang dapat di-query. Jika tidak ada batas idempotensi yang dapat dibangun, Anda tidak dapat menjamin bahwa replay setelah crash bebas dari efek duplikat.

Lanjutan 4: Apa yang berubah jika bisnis kemudian membutuhkan keterurutan ketat di seluruh tenant?

Maka tenant_id menjadi domain keterurutan yang tidak dapat dibagi, dan konkurensi lintas-pesanan tidak lagi valid. Jika satu tenant melebihi kapasitas satu partisi, optimalkan jalur serial tersebut, lakukan throttle pada tenant, atau negosiasikan ulang urutan event mana yang independen. Stream ter-shard yang diurutkan secara global dengan downstream merger dimungkinkan, tetapi itu memindahkan waktu tunggu pengurutan, penanganan celah, dan biaya ketersediaan ke consumer; ini bukan penskalaan yang cuma-cuma.

Lanjutan 5: Berapa lama waktu yang dibutuhkan untuk menguras backlog 27,6 juta record?

Input pertama-tama harus turun di bawah kapasitas pemrosesan. Jika throttling menurunkan input partisi panas menjadi 3.000 record per detik dan optimasi meningkatkan kapasitas pemrosesan menjadi 12.000, laju pengurasan bersih adalah 9.000:

text
27,600,000 ÷ 9,000 ≈ 3,067 seconds ≈ 51 minutes

Itu masih merupakan perkiraan laju konstan. Rencana pemulihan nyata menambahkan retry, throttling downstream, variasi ukuran record, dan margin keamanan, lalu terus merevisi estimasi dari lag slope yang teramati.

Lanjutan 6: Bagaimana Anda membuktikan bahwa tidak ada pesanan yang melintasi topik lama dan baru?

Simpan satu partitioning_version untuk setiap pesanan. Setiap producer membaca atau menyimpan cache dari record perutean berversi yang sama, dan versi tersebut hanya berubah setelah migration barrier berhasil. Consumer mencatat topik dan versi pertama yang terlihat untuk suatu pesanan, membunyikan peringatan jika suatu pesanan muncul di kedua rute aktif, dan menghentikan progres otomatis untuk pesanan tersebut. Selama uji beban dan canary rollout, rekonsiliasikan log producer, offset di kedua topik, dan urutan pesanan downstream daripada hanya memeriksa kesamaan jumlah total record.

Sumber publik

Pertanyaan terkait