Kami mencoba membuat Broker Layanan bekerja di lingkungan kami untuk menyelesaikan kasus bisnis. Saya tidak tahu apakah judul pesannya bagus, tetapi pertanyaan saya ada di bawah ini. Tapi itu mungkin bukan pertanyaan yang bagus, jadi setelah itu yang kita lakukan dan mengapa saya pikir itu pertanyaan yang tepat.
Berapa banyak pesan yang harus dikirim pada percakapan sebelum mengakhiri percakapan?
Kami ingin menggunakan Broker Layanan untuk memperbarui tabel hasil secara tidak sinkron. Tabel hasil diratakan dan cepat. Kami memiliki pemicu pada tabel dasar yang mengirim pesan dengan tabel dan kunci utama mereka. Kami memiliki tiga antrian:
- Latensi Rendah - objektif adalah 15 detik untuk diproses. Ini menangani item yang berubah terkait dengan item tertentu.
- Antrean Massal - sasaran adalah 5 menit untuk diproses. Ini menangani ketika sesuatu berubah yang memengaruhi ratusan (atau ribuan) item. Ini memecah daftar item yang terpengaruh dan mengumpankannya ke Antrian Latensi Rendah Ditangguhkan
- Latensi Rendah Ditangguhkan - objektif adalah 30 menit untuk diproses. Ini memproses item tetapi hanya dari antrian massal.
Pada dasarnya, jika informasi klien diperbarui; yang mempengaruhi banyak produk sehingga dikirim ke antrian massal untuk pemrosesan lebih lambat. Namun, jika suatu produk diperbarui, itu akan dikirim ke antrian latensi rendah.
Kami menggunakan kembali percakapan yang mirip dengan blog Remus Rusanu http://rusanu.com/2007/04/25/reusing-conversations/ , dengan pengecualian bahwa kami melakukannya berdasarkan modulus dari kunci utama. Ini memiliki manfaat tambahan karena membantu dalam menduplikasi kunci primer.
Jadi, kami menggunakan kembali percakapan dan berada dalam pedoman kami. Dengan dua utas, saya dapat membakar hingga 125 pesan / detik (setetes beberapa ribu pesan buatan), yang lebih dari sekadar mampu mengimbangi produksi (perkiraan 15 pesan / detik).
Namun, masalah yang kami alami adalah setelah jangka waktu tertentu, ~ 4 jam atau 120 ribu pesan, kami mulai melihat blok dan pertengkaran tinggi pada sysdesend dan tabel antrian. Kunci-kunci tersebut adalah LCK_M_U dan merupakan kunci-kunci KUNCI. Kadang-kadang hobt memutuskan untuk sysdesend dan lainnya ke tabel antrian tertentu (antrian_).
Kami memiliki proses yang akan mengakhiri percakapan setelah tidak aktif selama 24 jam atau 30 menit, sehingga kami dapat menambah waktu sebelum melanjutkan percakapan.
Kami menggunakan SQL 2016 Enterprise (13.0.4001.0)
- Trigger Fires (kirim ke latensi rendah atau massal)
- Cari atau buat gagang percakapan.
- mengirim pesan
- Prosedur antrian diaktifkan
- Perbarui tabel hasil
Proses pembersihan berjalan setiap 10 menit untuk melihat apakah ada percakapan kosong. jika menemukan mereka lebih dari tiga kali berturut-turut, itu menandainya sebagai tidak aktif dan mengakhiri percakapan.
Harap beri tahu saya jika ada detail tambahan yang mungkin bermanfaat. Saya tidak punya banyak pengalaman dengan Service Broker jadi saya tidak tahu apakah pesan / detik kami rendah, tinggi atau acuh tak acuh.
MEMPERBARUI
Jadi kami mencoba lagi hari ini dan mengalami masalah yang sama. Kami mengubah percakapan seumur hidup menjadi 2 jam dan itu tidak berpengaruh. Jadi kami kemudian menerapkan 150 trik; yang memiliki masalah yang sama.
Banyak menunggu di KIRIM KONVERSI, menunggu sysdesend. Adakah yang punya ide lebih lanjut?
PEMBARUAN 2
Kami menjalankan tes lebih lama hari ini dan untuk salah satu periode sampel 17 menit, kami memproses 41K pesan pada 4 pegangan percakapan. Kami mampu mengikuti kecuali menjelang akhir ketika kunci pada sysdesend dan meja antrian menjadi terlalu banyak dan kami mulai melayang di belakang sebelum menghentikannya. Kami tampaknya tidak memiliki masalah dalam memproses pesan, tanpa hal-hal memasuki antrian, kami dapat menariknya dan memprosesnya setidaknya 5x kecepatan itu. Kecepatan kami tampaknya terbatas berdasarkan penambahan pesan.
Pada pengujian selanjutnya, kami menghapus salah satu pemicu yang menyumbang 80% dari pesan. Bahkan dengan beban yang jauh berkurang ini, kami mulai melihat menunggu yang sama.
PEMBARUAN 3
Terima kasih, Remus atas saran Anda (dan terima kasih telah memposting artikel blog yang sangat baik tentang masalah ini, mereka sangat berperan dalam mencapai titik ini).
Kami menjalankannya lagi hari ini dan melakukan yang lebih baik (seperti kami pergi lebih lama sebelum melihat menunggu dan bahkan lebih lama sebelum itu melumpuhkan kami). Jadi, detailnya.
Kami mengubah: * Meningkatkan jumlah percakapan yang dipertahankan per utas dari 1: 1 menjadi 2: 1. Pada dasarnya, kami memiliki 8 pegangan percakapan untuk 4 utas.
- mengkonsolidasikan antrian massal (karena satu pesan masuk dapat berarti ratusan pesan keluar) untuk dikonsolidasikan ke dalam pesan yang lebih sedikit dan lebih besar.
Catatan tentang upaya ini:
menonaktifkan prosedur aktivasi antrian target. tidak ada perubahan dalam pemblokiran (kami menunggu 5 menit) dan pesannya dikirim ke sys.transmission_queues.
memonitor sys.conversation_endpoints. Angka ini naik dari 0 13K sangat cepat, dan kemudian lebih lambat naik sepanjang hari berakhir sekitar 25K setelah ~ 5 jam. Pemblokiran tidak mulai terjadi hingga mencapai 16K +/-
Saya pergi ke DAC dan menjalankan perintah DBREINDEX untuk antrian, meskipun dari permintaan, catatan hantu tidak pernah mencapai di atas 200 atau lebih sebelum pembersihan datang dan menurunkan hitungan ke 0.
sysdesend dan sysdercv memiliki jumlah yang identik 24.932 ketika saya mengakhiri tes.
kami memproses ~ 310 ribu pesan dalam 5 jam.
Kami pergi begitu lama sebelum semuanya berantakan sehingga saya benar-benar berpikir kami akan berhasil kali ini. Besok kami akan mencoba memaksa pesan untuk masuk melalui kawat.
sumber
we started seeing blocks and high contention on sysdesend and the queue table.
-> Apa jenis menunggu -PAGELATCH_EX/SH and WRITELOG
? Sudahkah Anda menggunakan 150 trik ? Jika tabel sistem adalah titik pertengkaran Anda, 150 trik akan sangat berguna.sys.conversation_endpoints
selama tes (konstan atau meningkat, dan seberapa besar itu ketika pemblokiran terjadi). 2) Ketika pemblokiran terjadi, apakah penonaktifan antrian target membuat perbedaan dalam pemblokiran KIRIM (menonaktifkan antrian harus merutekan KIRIM ke sys.transmission_queue). dan 3) Memaksa pesan untuk masuk ke wire, bahkan secara lokal (mengatur endpoint SSB, menambahkan rute) mengubah perilaku dalam jangka panjangALTER QUEUE ... REBUILD
membuat perbedaan setelah pemblokiran dimulai?Jawaban:
Saya tahu ini bentuk yang buruk untuk menjawab pertanyaan Anda sendiri, tetapi saya ingin menutup ini untuk siapa saja yang tertarik. Kami akhirnya berhasil menyelesaikan masalah, atau setidaknya menyelesaikannya cukup untuk memenuhi persyaratan kami. Saya ingin mengucapkan terima kasih kepada semua orang yang berkontribusi komentar; Remus Rusanu dan Kin karena mereka sangat membantu.
Basis data kami cukup sibuk dan dalam mode RCSI. Kami memiliki beberapa (ribuan) perangkat seluler yang memperbarui informasi lokasi mereka setiap 45 detik. Melalui pembaruan ini, beberapa tabel mendapatkan informasi mereka diperbarui (desain yang buruk, karena saya akan membatasi informasi yang mudah menguap ke satu tabel dan kemudian bergabung untuk hasilnya). Tabel-tabel ini adalah tabel yang sama yang kami coba untuk secara asinkron menghasilkan informasi pelaporan daripada meminta pengguna akhir langsung melawan tabel dasar.
Kami awalnya memiliki pemicu yang melakukan kursor di atas catatan yang dimodifikasi di setiap pernyataan pembaruan / penyisipan (seharusnya menjadi satu baris dalam kebanyakan kasus) dan mengirimkan setiap kunci utama dalam pesan ke broker layanan. Broker servis di dalam, terutama antrian massal adalah kursor lebih lanjut yang menjalankan prosedur pemberhentian untuk laporan (satu eksekusi per kunci utama).
Apa yang akhirnya membuat kami bekerja:
Kami menghapus kursor dan memutuskan mengirim pesan yang lebih besar. Masih satu pesan per transaksi pengguna per tabel, tetapi kami sekarang mengirim pesan dengan lebih dari satu kunci utama.
Prosesor massal juga mengirim beberapa kunci per pesan, yang mengurangi jumlah KIRIM KONVERSI yang terjadi saat mengacak pesan ke antrian lain yang sesuai.
Tabel yang paling tidak stabil (tabel data perangkat seluler kami) memiliki pemicunya dihapus. Kami memperbarui prosedur pemasangan untuk memasukkan kunci asing yang sesuai dan sekarang kami hanya bergabung kembali di meja itu ketika mengambil hasil kepada pengguna. Tabel ini dengan mudah menyumbang 80% dari pesan yang harus kami proses dalam sehari.
Kami memproses ~ 1 juta pesan sehari (tanpa tabel Seluler) dan sebagian besar (99% +) pesan kami diproses di dalam sasaran kami. Kami masih memiliki outlier sesekali tetapi mengingat sifat langka yang dianggap dapat diterima.
Faktor kontribusi:
Saya menemukan bug dalam prosedur pembersihan percakapan yang disebutkan sebelumnya yang tidak benar-benar membersihkan percakapan dengan tepat, dan mengakhiri secara prematur. Ini sekarang menghasilkan hitungan sysdesend kami tidak pernah lebih dari beberapa ribu (sebagian besar berasal dari menggunakan 150 trik).
Kursor pada pemicu tampaknya menahan lebih banyak penguncian daripada yang diantisipasi (bahkan dengan statis, forward_only). menghapus itu tampaknya telah membuat kunci yang kita lihat di KIRIM KONVERSI lebih bersifat sementara (atau setidaknya waktu yang kita lihat jauh lebih rendah).
Kami pada dasarnya menjalankan dua solusi berdampingan (backend solusi Broker Layanan (untuk pengujian di bawah beban produksi)) dan solusi saat ini (kueri mengerikan yang mencakup banyak tabel).
Sebagai manfaat sampingan, ini telah mengungkap masalah Pembersihan Catatan Hantu dan sementara itu tidak ada di tabel Pialang Layanan (sistem atau antrian), ini cukup merajalela di sistem kami dan gejalanya sejalan dengan sangat baik dengan "tidak ada alasan yang jelas". masalah yang sering kita alami. Investigasi sedang berlangsung tentang itu, kami mencoba untuk menemukan tabel yang berkontribusi padanya dan kami mungkin akan secara rutin membangun kembali indeks mereka.
Terima kasih sekali lagi.
sumber