Bagaimana Anda bisa membuat cluster menjalankan tugas hanya sekali?


13

Jika Anda memiliki tugas yang ingin Anda jalankan hanya sekali pada sekelompok server, secara berkala apa yang akan menjadi cara terbaik untuk mencapai ini? Definisi cluster dalam hal ini adalah 2 atau lebih server identik dengan sesi terdistribusi duduk di belakang load balancer.

Use Case: Anda memiliki tugas yang mahal untuk dijalankan yang seharusnya hanya dijalankan sekali per X jam. Pekerjaan ini misalnya dapat mengulangi banyak catatan dan memperbarui status mereka.

  • Skenario terburuk adalah bahwa menjalankan pekerjaan dua kali membuat data Anda tidak valid.
  • Skenario terbaik adalah pekerjaan menggunakan sumber daya di semua server Anda.

Ringkasan Persyaratan:

  1. Pekerjaan itu masih harus berjalan bahkan jika salah satu node sedang down.
  2. Pekerjaan hanya harus dijalankan sekali per jadwal.
  3. Jika beberapa pekerjaan dijadwalkan pada waktu yang sama atau pada waktu yang tumpang tindih, maka jumlah pekerjaan yang berjalan didistribusikan secara merata di antara server.
  4. Mesin harus memiliki basis kode yang sama dan disinkronkan melalui NTP.
  5. Konfigurasi mungkin berbeda antara simpul dan simpul, berdasarkan variabel lingkungan.
  6. Pekerjaan harus dimulai tepat waktu atau dalam interval waktu yang ditentukan yang diberikan. (misalnya 5 menit)

Solusi yang memungkinkan

  • Tetapkan satu simpul sebagai simpul utama, ini tidak berfungsi karena melanggar 1 di atas.
  • Buat permintaan agar penyeimbang muatan menyeimbangkan untuk memulai pekerjaan. Sayangnya ini memiliki efek samping bahwa jika Anda memiliki beberapa pekerjaan berjalan pada saat yang sama mereka semua dapat dijalankan oleh mesin yang sama.

Ini harus dijalankan di Jawa, dalam wadah servlet. Namun itu bukan coding pekerjaan yang saya cari.

Tentunya ini adalah masalah terpecahkan dengan solusi terbaik yang diketahui.


Pertanyaan terkait. /programming/5949038/schedule-job-executes-twice-on-cluster

Ini bukan duplikat karena solusinya tidak mencukupi sesuai dengan 5 persyaratan yang diberikan di atas. Solusi yang paling banyak dipilih mengalami masalah balapan, dan solusi kedua melanggar persyaratan 3

Jawaban:


16

Apakah Anda memiliki database bersama? Saya sudah melakukan ini dengan menggunakan database sebagai wasit di masa lalu.

Pada dasarnya, setiap "pekerjaan" direpresentasikan sebagai baris dalam basis data. Anda menjadwalkan pekerjaan dengan menambahkan baris ke basis data dengan waktu yang Anda inginkan dijalankan, kemudian setiap server melakukannya:

SELECT TOP 1 *
FROM jobs
WHERE state = 'NotRun'
ORDER BY run_time ASC

Dengan begitu, mereka semua akan memilih pekerjaan yang dijadwalkan untuk dijalankan berikutnya . Mereka semua tidur sehingga mereka bangun ketika pekerjaan itu seharusnya dijalankan. Kemudian, mereka semua melakukan ini:

UPDATE jobs
SET state = 'Running'
WHERE job_id = :id
  AND state = 'NotRun'

Di mana :idpengidentifikasi pekerjaan yang Anda dapatkan pada langkah di atas. Karena pembaruannya bersifat atomik, hanya satu dari server yang benar-benar akan memperbarui baris, Anda dapat memeriksa kode status "jumlah baris pembaruan" database untuk menentukan apakah Anda adalah server yang benar-benar memperbarui baris, dan oleh karena itu apakah Anda server. yang bisa menjalankan pekerjaan.

Jika Anda tidak "menang" dan Anda tidak menjalankan pekerjaan, segera kembali ke langkah 1 segera. Jika Anda "menang", jadwalkan pekerjaan untuk dieksekusi di utas lain, lalu tunggu beberapa detik sebelum kembali ke langkah 1. Dengan begitu, server yang tidak mendapatkan pekerjaan saat ini lebih mungkin untuk mengambil pekerjaan itu dijadwalkan untuk segera dijalankan.


1
Apa tingkat isolasi yang Anda gunakan di sini? Baca berkomitmen atau bersambung?
Maverick Riz

2

Beberapa server aplikasi memiliki fitur untuk "layanan singleton lebar klaster".

Misalnya Weblogic memiliki fitur Layanan Singleton yang dikonfigurasi melalui konsol admin web.

Anda harus menulis kelas yang mengimplementasikan weblogic.cluster.singleton.SingletonService dan menggunakannya untuk mendeklarasikan layanan di konsol admin. Cluster menangani instantiating kelas dan memberi tahu Anda ketika layanan dimulai atau dihentikan. Antarmuka SingletonService memiliki metode aktifkan () dan nonaktifkan ().

Panggilan Weblogic mengaktifkan () ketika pertama kali membuka layanan di salah satu node cluster. Jika simpul yang dipilih turun, server admin "memindahkan" layanan pada server yang berbeda, memanggil aktifkan () di sana.

http://docs.oracle.com/cd/E12839_01/apirefs.1111/e13952/taskhelp/clusters/ConfigureSingletonService.html

Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.