Solid Queue คือแบ็กเอนด์การจัดคิวบน DB สำหรับ Active Job ซึ่งออกแบบโดยคำนึงถึงความเรียบง่ายและประสิทธิภาพเป็นหลัก
นอกเหนือจากการจัดคิวและประมวลผลงานปกติแล้ว Solid Queue ยังรองรับงานที่ล่าช้า การควบคุมการทำงานพร้อมกัน งานที่เกิดซ้ำ การหยุดคิว ลำดับความสำคัญที่เป็นตัวเลขต่องาน ลำดับความสำคัญตามลำดับคิว และการเข้าคิวจำนวนมาก ( enqueue_all
สำหรับ Active Job's perform_all_later
)
Solid Queue สามารถใช้กับฐานข้อมูล SQL เช่น MySQL, PostgreSQL หรือ SQLite และใช้ประโยชน์จาก FOR UPDATE SKIP LOCKED
clause (หากมี) เพื่อหลีกเลี่ยงการบล็อกและการรอการล็อคเมื่อทำการโพล โดยอาศัย Active Job ในการลองใหม่ การยกเลิก การจัดการข้อผิดพลาด การทำให้เป็นอนุกรม หรือความล่าช้า และเข้ากันได้กับมัลติเธรดของ Ruby on Rails
Solid Queue ได้รับการกำหนดค่าตามค่าเริ่มต้นในแอปพลิเคชัน Rails 8 ใหม่ แต่ถ้าคุณใช้เวอร์ชันก่อนหน้า คุณสามารถเพิ่มได้ด้วยตนเองโดยทำตามขั้นตอนเหล่านี้:
bundle add solid_queue
bin/rails solid_queue:install
สิ่งนี้จะกำหนดค่า Solid Queue เป็นแบ็คเอนด์งานที่ใช้งานจริงที่ใช้งานจริง สร้างไฟล์การกำหนดค่า config/queue.yml
และ config/recurring.yml
และสร้าง db/queue_schema.rb
นอกจากนี้ยังจะสร้าง wrapper ปฏิบัติการ bin/jobs
ที่คุณสามารถใช้เพื่อเริ่ม Solid Queue
เมื่อคุณดำเนินการดังกล่าวแล้ว คุณจะต้องเพิ่มการกำหนดค่าสำหรับฐานข้อมูลคิวใน config/database.yml
หากคุณใช้ SQLite จะมีลักษณะดังนี้:
production :
primary :
<< : *default
database : storage/production.sqlite3
queue :
<< : *default
database : storage/production_queue.sqlite3
migrations_paths : db/queue_migrate
...หรือหากคุณใช้ MySQL/PostgreSQL/Trilogy:
production :
primary : &primary_production
<< : *default
database : app_production
username : app
password : <%= ENV["APP_DATABASE_PASSWORD"] %>
queue :
<< : *primary_production
database : app_production_queue
migrations_paths : db/queue_migrate
หมายเหตุ: การเรียก bin/rails solid_queue:install
จะเพิ่ม config.solid_queue.connects_to = { database: { writing: :queue } }
ไปยัง config/environments/production.rb
โดยอัตโนมัติ ดังนั้นจึงไม่จำเป็นต้องกำหนดค่าเพิ่มเติมที่นั่น (แม้ว่าคุณจะต้องแน่ใจว่า ที่คุณใช้ชื่อ queue
ใน database.yml
เพื่อให้ตรงกัน!) แต่หากคุณต้องการใช้ Solid Queue ในสภาพแวดล้อมอื่น (เช่น การจัดเตรียมหรือการพัฒนา) คุณจะต้องเพิ่มบรรทัด config.solid_queue.connects_to
ลงในไฟล์สภาพแวดล้อมที่เกี่ยวข้องด้วยตนเอง และเช่นเคย ตรวจสอบให้แน่ใจว่าชื่อที่คุณใช้สำหรับฐานข้อมูลใน config/database.yml
ตรงกับชื่อที่คุณใช้ใน config.solid_queue.connects_to
จากนั้นรัน db:prepare
ในการผลิตเพื่อให้แน่ใจว่าฐานข้อมูลถูกสร้างขึ้นและโหลดสคีมาแล้ว
ตอนนี้คุณพร้อมที่จะเริ่มประมวลผลงานด้วยการรัน bin/jobs
บนเซิร์ฟเวอร์ที่กำลังทำงานอยู่ นี่จะเริ่มประมวลผลงานในทุกคิวโดยใช้การกำหนดค่าเริ่มต้น ดูด้านล่างเพื่อเรียนรู้เพิ่มเติมเกี่ยวกับการกำหนดค่า Solid Queue
สำหรับโปรเจ็กต์ขนาดเล็ก คุณสามารถรัน Solid Queue บนเครื่องเดียวกับเว็บเซิร์ฟเวอร์ของคุณได้ เมื่อคุณพร้อมที่จะปรับขนาด Solid Queue รองรับการปรับขนาดแนวนอนได้ทันทีที่แกะกล่อง คุณสามารถเรียกใช้ Solid Queue บนเซิร์ฟเวอร์แยกต่างหากจากเว็บเซิร์ฟเวอร์ของคุณ หรือแม้แต่เรียกใช้ bin/jobs
บนเครื่องหลายเครื่องพร้อมกันได้ ขึ้นอยู่กับการกำหนดค่า คุณสามารถกำหนดให้เครื่องบางเครื่องรันเฉพาะผู้จัดส่งหรือผู้ปฏิบัติงานเท่านั้น ดูส่วนการกำหนดค่าสำหรับรายละเอียดเพิ่มเติมเกี่ยวกับเรื่องนี้
หมายเหตุ : การเปลี่ยนแปลงสคีมาในอนาคตจะมาในรูปแบบของการย้ายข้อมูลตามปกติ
แนะนำให้เรียกใช้ Solid Queue ในฐานข้อมูลแยกต่างหาก แต่ก็เป็นไปได้ที่จะใช้ฐานข้อมูลเดียวสำหรับทั้งแอปและคิว เพียงทำตามขั้นตอนเหล่านี้:
db/queue_schema.rb
ไปยังการย้ายปกติและลบ db/queue_schema.rb
config.solid_queue.connects_to
ออกจาก production.rb
bin/jobs
แล้ว คุณจะไม่มีหลายฐานข้อมูล ดังนั้น database.yml
จึงไม่จำเป็นต้องมีฐานข้อมูลหลักและฐานข้อมูลคิว
หากคุณวางแผนที่จะใช้ Solid Queue ทีละน้อยโดยการสลับงานหนึ่งงานในแต่ละครั้ง คุณสามารถทำได้โดยปล่อยให้ config.active_job.queue_adapter
ตั้งค่าเป็นแบ็กเอนด์เก่าของคุณ จากนั้นตั้งค่า queue_adapter
โดยตรงในงานที่คุณกำลังย้าย:
# app/jobs/my_job.rb
class MyJob < ApplicationJob
self . queue_adapter = :solid_queue
# ...
end
Solid Queue ได้รับการออกแบบมาเพื่อการรับส่งข้อมูลสูงสุดเมื่อใช้กับ MySQL 8+ หรือ PostgreSQL 9.5+ เนื่องจากรองรับ FOR UPDATE SKIP LOCKED
คุณสามารถใช้กับเวอร์ชันเก่าได้ แต่ในกรณีนี้ คุณอาจประสบปัญหาการรอล็อกหากคุณเรียกใช้ผู้ปฏิบัติงานหลายคนในคิวเดียวกัน คุณยังสามารถใช้กับ SQLite บนแอปพลิเคชันขนาดเล็กได้อีกด้วย
เรามีนักแสดงหลายประเภทใน Solid Queue:
solid_queue_ready_executions
solid_queue_scheduled_executions
ไปยังตาราง solid_queue_ready_executions
เพื่อให้ผู้ปฏิบัติงานสามารถรับงานเหล่านั้นได้ ยิ่งไปกว่านั้น พวกเขายังทำงานบำรุงรักษาที่เกี่ยวข้องกับการควบคุมการทำงานพร้อมกันอีกด้วยหัวหน้างานของ Solid Queue จะแยกกระบวนการแยกต่างหากสำหรับผู้ปฏิบัติงาน/ผู้จัดส่ง/ผู้จัดกำหนดการแต่ละคน
ตามค่าเริ่มต้น Solid Queue จะพยายามค้นหาการกำหนดค่าของคุณภายใต้ config/queue.yml
แต่คุณสามารถตั้งค่าเส้นทางอื่นได้โดยใช้ตัวแปรสภาพแวดล้อม SOLID_QUEUE_CONFIG
หรือโดยใช้ตัวเลือก -c/--config_file
กับ bin/jobs
เช่นนี้:
bin/jobs -c config/calendar.yml
นี่คือลักษณะการกำหนดค่านี้:
production :
dispatchers :
- polling_interval : 1
batch_size : 500
concurrency_maintenance_interval : 300
workers :
- queues : " * "
threads : 3
polling_interval : 2
- queues : [ real_time, background ]
threads : 5
polling_interval : 0.1
processes : 3
ทุกอย่างเป็นทางเลือก หากไม่มีการกำหนดค่าไว้เลย Solid Queue จะทำงานโดยมีผู้มอบหมายงานหนึ่งคนและผู้ปฏิบัติงานหนึ่งคนที่มีการตั้งค่าเริ่มต้น หากคุณต้องการรันเฉพาะผู้จัดส่งหรือผู้ปฏิบัติงาน คุณเพียงแค่ต้องรวมส่วนนั้นเพียงอย่างเดียวในการกำหนดค่า ตัวอย่างเช่น ด้วยการกำหนดค่าต่อไปนี้:
production :
dispatchers :
- polling_interval : 1
batch_size : 500
concurrency_maintenance_interval : 300
หัวหน้างานจะมีผู้มอบหมายงาน 1 คนและไม่มีพนักงาน
ภาพรวมของตัวเลือกต่างๆ มีดังนี้
polling_interval
: ช่วงเวลาเป็นวินาทีที่ผู้ปฏิบัติงานและผู้มอบหมายงานจะรอก่อนที่จะตรวจสอบงานเพิ่มเติม เวลานี้เริ่มต้นที่ 1
วินาทีสำหรับผู้มอบหมายงาน และ 0.1
วินาทีสำหรับผู้ปฏิบัติงาน
batch_size
: ผู้มอบหมายงานจะจัดส่งงานเป็นชุดขนาดนี้ ค่าเริ่มต้นคือ 500
concurrency_maintenance_interval
: ช่วงเวลาเป็นวินาทีที่ผู้มอบหมายงานจะรอก่อนที่จะตรวจสอบงานที่ถูกบล็อกซึ่งสามารถปลดบล็อกได้ อ่านเพิ่มเติมเกี่ยวกับการควบคุมการทำงานพร้อมกันเพื่อเรียนรู้เพิ่มเติมเกี่ยวกับการตั้งค่านี้ มีค่าเริ่มต้นอยู่ที่ 600
วินาที
queues
: รายการคิวที่พนักงานจะเลือกงาน คุณสามารถใช้ *
เพื่อระบุคิวทั้งหมด (ซึ่งเป็นค่าเริ่มต้นและลักษณะการทำงานที่คุณจะได้รับหากคุณละเว้นสิ่งนี้) คุณสามารถระบุคิวเดียวหรือรายการคิวเป็นอาร์เรย์ได้ งานจะถูกสำรวจจากคิวเหล่านั้นตามลำดับ ดังนั้น ตัวอย่างเช่น ด้วย [ real_time, background ]
จะไม่มีงานใดที่จะถูกดึงออกจาก background
เว้นแต่จะไม่มีงานรออยู่ใน real_time
อีกต่อไป คุณยังสามารถระบุคำนำหน้าด้วยไวด์การ์ดเพื่อจับคู่คิวที่ขึ้นต้นด้วยคำนำหน้าได้ ตัวอย่างเช่น:
staging :
workers :
- queues : staging*
threads : 3
polling_interval : 5
สิ่งนี้จะสร้างผู้ปฏิบัติงานดึงงานจากคิวทั้งหมดโดยเริ่มจาก staging
ไวด์การ์ด *
ได้รับอนุญาตเฉพาะตัวมันเองหรือที่ส่วนท้ายของชื่อคิวเท่านั้น คุณไม่สามารถระบุชื่อคิวเช่น *_some_queue
ได้ สิ่งเหล่านี้จะถูกละเว้น
สุดท้าย คุณสามารถรวมคำนำหน้าเข้ากับชื่อที่ตรงกันทุกประการ เช่น [ staging*, background ]
และลักษณะการทำงานที่เกี่ยวข้องกับลำดับจะเหมือนกันกับชื่อที่ตรงกันเท่านั้น
ตรวจสอบส่วนด้านล่างเกี่ยวกับวิธีการทำงานของลำดับคิวรวมกับลำดับความสำคัญ และวิธีที่คุณระบุคิวต่อผู้ปฏิบัติงานอาจส่งผลต่อประสิทธิภาพการทำงานอย่างไร
threads
: นี่คือขนาดสูงสุดของเธรดพูลที่ผู้ปฏิบัติงานแต่ละคนจะต้องรันงาน ผู้ปฏิบัติงานแต่ละคนจะดึงงานจำนวนนี้จากคิวของตนเป็นอย่างมากที่สุด และจะโพสต์งานเหล่านั้นลงในกลุ่มเธรดที่จะรัน โดยค่าเริ่มต้น นี่คือ 3
เฉพาะผู้ปฏิบัติงานเท่านั้นที่มีการตั้งค่านี้
processes
: นี่คือจำนวนกระบวนการของผู้ปฏิบัติงานที่หัวหน้างานจะแยกจากการตั้งค่าที่กำหนด โดยค่าเริ่มต้น นี่คือ 1
เพียงกระบวนการเดียว การตั้งค่านี้มีประโยชน์หากคุณต้องการจัดสรร CPU คอร์มากกว่าหนึ่งคอร์ให้กับคิวหรือคิวที่มีการกำหนดค่าเดียวกัน เฉพาะผู้ปฏิบัติงานเท่านั้นที่มีการตั้งค่านี้
concurrency_maintenance
: ไม่ว่าผู้ส่งจะดำเนินการบำรุงรักษาการทำงานพร้อมกันหรือไม่ สิ่งนี้เป็น true
ตามค่าเริ่มต้น และจะมีประโยชน์หากคุณไม่ได้ใช้การควบคุมการทำงานพร้อมกันใดๆ และต้องการปิดการใช้งาน หรือหากคุณใช้งานโปรแกรมเลือกจ่ายงานหลายคน และต้องการให้บางโปรแกรมสั่งงานโดยไม่ต้องทำอะไรอย่างอื่น
ตามที่กล่าวไว้ข้างต้น หากคุณระบุรายการคิวสำหรับผู้ปฏิบัติงาน คิวเหล่านี้จะถูกสำรวจตามลำดับที่กำหนด เช่น สำหรับรายการ real_time,background
จะไม่มีงานใดถูกดึงออกจาก background
เว้นแต่จะไม่มีงานรออยู่อีกต่อไป real_time
งานที่ใช้งานอยู่ยังสนับสนุนลำดับความสำคัญของจำนวนเต็มบวกเมื่อจัดคิวงาน ใน Solid Queue ค่ายิ่งน้อย ลำดับความสำคัญก็จะยิ่งสูงขึ้น ค่าเริ่มต้นคือ 0
สิ่งนี้มีประโยชน์เมื่อคุณรันงานที่มีความสำคัญหรือเร่งด่วนต่างกันในคิวเดียวกัน ภายในคิวเดียวกัน งานจะถูกเลือกตามลำดับความสำคัญ แต่ในรายการคิว ลำดับคิวจะมีความสำคัญกว่า ดังนั้นในตัวอย่างก่อนหน้าที่มี real_time,background
งานในคิว real_time
จะถูกเลือกก่อนที่งานใน background
แม้ว่าคิวใน background
จะมีการตั้งค่าลำดับความสำคัญที่สูงกว่า (ค่าน้อยกว่า) ก็ตาม
เราขอแนะนำไม่ให้ผสมลำดับคิวกับลำดับความสำคัญ แต่ให้เลือกอย่างใดอย่างหนึ่ง เนื่องจากจะทำให้คำสั่งในการปฏิบัติงานตรงไปตรงมามากขึ้นสำหรับคุณ
เพื่อรักษาประสิทธิภาพการโพลและให้แน่ใจว่ามีการใช้ดัชนีที่ครอบคลุมอยู่เสมอ Solid Queue จะทำแบบสอบถามการโพลเพียงสองประเภทเท่านั้น:
-- No filtering by queue
SELECT job_id
FROM solid_queue_ready_executions
ORDER BY priority ASC , job_id ASC
LIMIT ?
FOR UPDATE SKIP LOCKED;
-- Filtering by a single queue
SELECT job_id
FROM solid_queue_ready_executions
WHERE queue_name = ?
ORDER BY priority ASC , job_id ASC
LIMIT ?
FOR UPDATE SKIP LOCKED;
อันแรก (ไม่มีการกรองตามคิว) จะถูกใช้เมื่อคุณระบุ
queues : *
และไม่มีคิวใดๆ ที่ถูกหยุดชั่วคราว เนื่องจากเราต้องการกำหนดเป้าหมายคิวทั้งหมด
ในกรณีอื่นๆ เราจำเป็นต้องมีรายการคิวที่จะกรองตามลำดับ เนื่องจากเราสามารถกรองได้ทีละคิวเท่านั้นเพื่อให้แน่ใจว่าเราใช้ดัชนีในการเรียงลำดับ ซึ่งหมายความว่าหากคุณระบุคิวของคุณเป็น:
queues : beta*
เราจะต้องได้รับรายการคิวที่มีอยู่ทั้งหมดที่ตรงกับคำนำหน้านั้นก่อน โดยมีข้อความค้นหาที่มีลักษณะดังนี้:
SELECT DISTINCT (queue_name)
FROM solid_queue_ready_executions
WHERE queue_name LIKE ' beta% ' ;
การสืบค้น DISTINCT
ประเภทนี้ในคอลัมน์ที่เป็นคอลัมน์ซ้ายสุดในดัชนีสามารถทำได้อย่างรวดเร็วใน MySQL ด้วยเทคนิคที่เรียกว่า Loose Index Scan อย่างไรก็ตาม PostgreSQL และ SQLite ไม่ได้ใช้เทคนิคนี้ ซึ่งหมายความว่าหากตาราง solid_queue_ready_executions
ของคุณมีขนาดใหญ่มากเนื่องจากคิวของคุณลึกมาก การสืบค้นนี้จะช้าลง โดยปกติตาราง solid_queue_ready_executions
ของคุณจะมีขนาดเล็ก แต่ก็สามารถเกิดขึ้นได้
เช่นเดียวกับการใช้คำนำหน้า สิ่งเดียวกันนี้จะเกิดขึ้นหากคุณหยุดคิวชั่วคราว เนื่องจากเราจำเป็นต้องได้รับรายการคิวทั้งหมดที่มีการสืบค้นเช่น
SELECT DISTINCT (queue_name)
FROM solid_queue_ready_executions
แล้วลบรายการที่หยุดชั่วคราวออก การหยุดชั่วคราวโดยทั่วไปควรเป็นสิ่งที่หาได้ยาก ใช้ในสถานการณ์พิเศษ และในช่วงเวลาสั้นๆ หากคุณไม่ต้องการประมวลผลงานจากคิวอีกต่อไป วิธีที่ดีที่สุดคือการลบงานออกจากรายการคิวของคุณ
โดยสรุป หากคุณต้องการให้แน่ใจว่าการโพลมีประสิทธิภาพสูงสุด วิธีที่ดีที่สุดคือระบุชื่อให้ถูกต้องเสมอ และไม่มีการหยุดคิวใดๆ ชั่วคราว
ทำสิ่งนี้:
queues : background, backend
แทนสิ่งนี้:
queues : back*
ผู้ปฏิบัติงานใน Solid Queue ใช้เธรดพูลเพื่อรันงานในหลายเธรด กำหนดค่าได้ผ่านพารามิเตอร์ threads
ด้านบน นอกจากนี้ การทำงานแบบขนานสามารถทำได้ผ่านกระบวนการต่างๆ ในเครื่องเดียว (กำหนดค่าได้ผ่านพนักงานที่แตกต่างกันหรือพารามิเตอร์ processes
ด้านบน) หรือโดยการปรับขนาดแนวนอน
หัวหน้างานมีหน้าที่จัดการกระบวนการเหล่านี้ และตอบสนองต่อสัญญาณต่อไปนี้:
TERM
, INT
: เริ่มต้นการยกเลิกอย่างสง่างาม หัวหน้างานจะส่งสัญญาณ TERM
ไปยังกระบวนการที่ได้รับการดูแล และจะรอจนถึงเวลา SolidQueue.shutdown_timeout
จนกว่าจะเสร็จสิ้น หากกระบวนการที่ได้รับการดูแลยังคงอยู่ภายในเวลานั้น ระบบจะส่งสัญญาณ QUIT
ไปยังพวกเขาเพื่อระบุว่าต้องออกQUIT
: เริ่มการยกเลิกทันที หัวหน้างานจะส่งสัญญาณ QUIT
ไปยังกระบวนการที่ได้รับการดูแล ทำให้พวกเขาออกจากระบบทันที เมื่อได้รับสัญญาณ QUIT
หากผู้ปฏิบัติงานยังคงมีงานอยู่ในเที่ยวบิน งานเหล่านี้จะถูกส่งกลับไปยังคิวเมื่อกระบวนการถูกยกเลิกการลงทะเบียน
หากกระบวนการไม่มีโอกาสทำความสะอาดก่อนที่จะออก (เช่น หากมีผู้ดึงสายเคเบิลไปที่ใดที่หนึ่ง) งานบนเครื่องบินอาจยังคงอ้างสิทธิ์โดยกระบวนการที่ดำเนินการเหล่านั้น กระบวนการส่งฮาร์ทบีท และผู้บังคับบัญชาจะตรวจสอบและตัดกระบวนการที่มีฮาร์ทบีทที่หมดอายุ ซึ่งจะปล่อยงานที่อ้างสิทธิ์ใดๆ กลับไปยังคิวของพวกเขา คุณสามารถกำหนดค่าทั้งความถี่ของการเต้นของหัวใจและเกณฑ์เพื่อพิจารณาว่ากระบวนการไม่ทำงาน ดูส่วนด้านล่างสำหรับสิ่งนี้
คุณสามารถกำหนดค่าฐานข้อมูลที่ใช้โดย Solid Queue ผ่านตัวเลือก config.solid_queue.connects_to
ในไฟล์กำหนดค่า config/application.rb
หรือ config/environments/production.rb
ตามค่าเริ่มต้น ฐานข้อมูลเดียวจะถูกใช้สำหรับทั้งการเขียนและการอ่านที่เรียกว่า queue
เพื่อให้ตรงกับการกำหนดค่าฐานข้อมูลที่คุณตั้งค่าระหว่างการติดตั้ง
สามารถใช้ตัวเลือกทั้งหมดที่ Active Record สำหรับหลายฐานข้อมูลได้ที่นี่
ใน Solid Queue คุณสามารถเชื่อมโยงจุดต่างๆ ในชีวิตของหัวหน้างานได้สองจุด:
start
: หลังจากที่หัวหน้างานบูทเสร็จแล้ว และก่อนที่มันจะแยกพนักงานและผู้มอบหมายงานstop
: หลังจากรับสัญญาณ ( TERM
, INT
หรือ QUIT
) และก่อนที่จะเริ่มการปิดระบบอย่างสง่างามหรือทันทีและแบ่งเป็นสองจุดในชีวิตของคนงาน:
worker_start
: หลังจากที่ผู้ปฏิบัติงานบูทเสร็จแล้วและก่อนที่จะเริ่มการวนซ้ำworker_stop
: หลังจากรับสัญญาณ ( TERM
, INT
หรือ QUIT
) และก่อนที่จะเริ่มการปิดระบบอย่างสง่างามหรือทันที (ซึ่งเพิ่ง exit!
)คุณสามารถใช้วิธีการต่อไปนี้กับบล็อกเพื่อทำสิ่งนี้:
SolidQueue . on_start
SolidQueue . on_stop
SolidQueue . on_worker_start
SolidQueue . on_worker_stop
ตัวอย่างเช่น:
SolidQueue . on_start { start_metrics_server }
SolidQueue . on_stop { stop_metrics_server }
สิ่งเหล่านี้สามารถเรียกได้หลายครั้งเพื่อเพิ่ม hooks หลายอัน แต่จะต้องเกิดขึ้นก่อนที่ Solid Queue จะเริ่มทำงาน ตัวเริ่มต้นจะเป็นสถานที่ที่ดีในการทำเช่นนี้
หมายเหตุ : การตั้งค่าในส่วนนี้ควรตั้งค่าไว้ใน config/application.rb
หรือการกำหนดค่าสภาพแวดล้อมของคุณดังนี้: config.solid_queue.silence_polling = true
มีการตั้งค่าหลายอย่างที่ควบคุมวิธีการทำงานของ Solid Queue ซึ่งคุณสามารถตั้งค่าได้เช่นกัน:
logger
: คนตัดไม้ที่คุณต้องการให้ Solid Queue ใช้ ค่าเริ่มต้นคือตัวบันทึกแอป
app_executor
: ตัวดำเนินการ Rails ที่ใช้ในการตัดการดำเนินการแบบอะซิงโครนัส โดยมีค่าเริ่มต้นเป็นตัวดำเนินการแอป
on_thread_error
: lambda/Proc ที่กำหนดเองเพื่อโทรเมื่อมีข้อผิดพลาดภายในเธรด Solid Queue ที่รับข้อยกเว้นที่ยกมาเป็นอาร์กิวเมนต์ ค่าเริ่มต้นเป็น
-> ( exception ) { Rails . error . report ( exception , handled : false ) }
สิ่งนี้ไม่ได้ใช้สำหรับข้อผิดพลาดที่เกิดขึ้นภายในการปฏิบัติงาน ข้อผิดพลาดที่เกิดขึ้นในงานได้รับการจัดการโดย retry_on
หรือ discard_on
ของ Active Job และท้ายที่สุดจะส่งผลให้งานที่ล้มเหลว นี่เป็นข้อผิดพลาดที่เกิดขึ้นภายใน Solid Queue เอง
use_skip_locked
: จะใช้ FOR UPDATE SKIP LOCKED
เมื่อทำการล็อคการอ่านหรือไม่ สิ่งนี้จะถูกตรวจพบโดยอัตโนมัติในอนาคต และในตอนนี้ คุณจะต้องตั้งค่านี้เป็น false
หากฐานข้อมูลของคุณไม่รองรับ สำหรับ MySQL นั่นจะเป็นเวอร์ชัน < 8 และสำหรับ PostgreSQL เวอร์ชัน < 9.5 หากคุณใช้ SQLite สิ่งนี้จะไม่มีผลใดๆ เนื่องจากการเขียนจะเป็นไปตามลำดับ
process_heartbeat_interval
: ช่วงเวลาการเต้นของหัวใจที่กระบวนการทั้งหมดจะตามมา—ค่าเริ่มต้นคือ 60 วินาที
process_alive_threshold
: ระยะเวลาในการรอจนกว่ากระบวนการจะถือว่าหยุดทำงานหลังจากการเต้นของหัวใจครั้งสุดท้าย—ค่าเริ่มต้นคือ 5 นาที
shutdown_timeout
: เวลาที่หัวหน้างานจะรอเนื่องจากส่งสัญญาณ TERM
ไปยังกระบวนการที่ได้รับการดูแลก่อนที่จะส่งเวอร์ชัน QUIT
ไปให้พวกเขาเพื่อขอยุติการทำงานทันที โดยค่าเริ่มต้นอยู่ที่ 5 วินาที
silence_polling
: จะปิดเสียงบันทึก Active Record ที่ปล่อยออกมาเมื่อทำการโพลสำหรับทั้งผู้ปฏิบัติงานและผู้มอบหมายงานหรือไม่—ค่าเริ่มต้นคือ true
supervisor_pidfile
: พาธไปยัง pidfile ที่หัวหน้างานจะสร้างเมื่อทำการบูท เพื่อป้องกันการเรียกใช้หัวหน้างานมากกว่าหนึ่งคนในโฮสต์เดียวกัน หรือในกรณีที่คุณต้องการใช้เพื่อตรวจสุขภาพ nil
เลยตามค่าเริ่มต้น
preserve_finished_jobs
: ว่าจะเก็บงานที่เสร็จแล้วไว้ในตาราง solid_queue_jobs
หรือไม่—มีค่าเริ่มต้นเป็น true
clear_finished_jobs_after
: ระยะเวลาที่จะคงงานที่เสร็จแล้วไว้ ในกรณีที่ preserve_finished_jobs
เป็นจริง โดยค่าเริ่มต้นคือ 1 วัน หมายเหตุ: ขณะนี้ ไม่มีการล้างข้อมูลงานที่เสร็จแล้วโดยอัตโนมัติ คุณต้องทำสิ่งนี้โดยการเรียกใช้ SolidQueue::Job.clear_finished_in_batches
เป็นระยะ แต่สิ่งนี้จะเกิดขึ้นโดยอัตโนมัติในอนาคตอันใกล้นี้
default_concurrency_control_period
: ค่าที่จะใช้เป็นค่าเริ่มต้นสำหรับพารามิเตอร์ duration
ในการควบคุมการทำงานพร้อมกัน โดยมีค่าเริ่มต้นอยู่ที่ 3 นาที
Solid Queue จะเพิ่ม SolidQueue::Job::EnqueueError
สำหรับข้อผิดพลาด Active Record ใด ๆ ที่เกิดขึ้นเมื่อเข้าคิวงาน เหตุผลที่ไม่เพิ่ม ActiveJob::EnqueueError
ก็คืออันนี้ได้รับการจัดการโดย Active Job ทำให้ perform_later
ส่งคืน false
และตั้งค่า job.enqueue_error
ทำให้งานเป็นบล็อกที่คุณต้องส่งผ่านไปยัง perform_later
สิ่งนี้ทำงานได้ดีมากสำหรับงานของคุณเอง แต่ทำให้การจัดการความล้มเหลวยากมากสำหรับงานที่เข้าคิวโดย Rails หรืออัญมณีอื่น ๆ เช่น Turbo::Streams::BroadcastJob
หรือ ActiveStorage::AnalyzeJob
เนื่องจากคุณไม่ได้ควบคุมการเรียกเพื่อ perform_later
ในกรณีนั้น
ในกรณีของงานที่เกิดซ้ำ หากเกิดข้อผิดพลาดดังกล่าวเมื่อจัดคิวงานที่สอดคล้องกับงาน งานนั้นจะถูกจัดการและบันทึกแต่จะไม่เกิดฟองขึ้น
Solid Queue ขยายงานที่ใช้งานอยู่ด้วยการควบคุมการทำงานพร้อมกัน ซึ่งช่วยให้คุณสามารถจำกัดจำนวนงานบางประเภทหรืออาร์กิวเมนต์บางอย่างที่สามารถรันได้ในเวลาเดียวกัน เมื่อจำกัดด้วยวิธีนี้ งานจะถูกบล็อกไม่ให้ทำงาน และงานเหล่านั้นจะยังคงถูกบล็อกจนกว่างานอื่นจะเสร็จสิ้นและเลิกบล็อก หรือหลังจากเวลาหมดอายุที่ตั้งไว้ ( ระยะเวลา ของขีดจำกัดการทำงานพร้อมกัน ) ผ่านไป งานจะไม่ถูกทิ้งหรือสูญหาย มีแต่ถูกบล็อกเท่านั้น
class MyJob < ApplicationJob
limits_concurrency to : max_concurrent_executions , key : -> ( arg1 , arg2 , ** ) { ... } , duration : max_interval_to_guarantee_concurrency_limit , group : concurrency_group
# ...
key
เป็นพารามิเตอร์ที่จำเป็นเท่านั้น และอาจเป็นสัญลักษณ์ สตริง หรือ proc ที่ได้รับอาร์กิวเมนต์ของงานเป็นพารามิเตอร์ และจะถูกใช้เพื่อระบุงานที่จำเป็นต้องจำกัดร่วมกัน หาก proc ส่งคืนบันทึก Active Record คีย์จะถูกสร้างขึ้นจากชื่อคลาสและ id
to
1
โดยค่าเริ่มต้นduration
ถูกตั้งค่าเป็น SolidQueue.default_concurrency_control_period
โดยค่าเริ่มต้น ซึ่งตัวมันเองมีค่าเริ่มต้นอยู่ที่ 3 minutes
แต่คุณสามารถกำหนดค่าได้เช่นกันgroup
ใช้เพื่อควบคุมการทำงานพร้อมกันของคลาสงานต่างๆ ร่วมกัน โดยค่าเริ่มต้นจะเป็นชื่อคลาสงาน เมื่องานมีการควบคุมเหล่านี้ เราจะตรวจสอบให้แน่ใจว่าจำนวนงานสูงสุด (ระบุเป็น to
) ที่ให้ key
เดียวกันจะถูกดำเนินการพร้อมกัน และการรับประกันนี้จะคงอยู่ตาม duration
สำหรับแต่ละงานที่อยู่ในคิว โปรดทราบว่าไม่มีการรับประกันเกี่ยวกับ ลำดับการดำเนินการ เฉพาะงานที่ดำเนินการในเวลาเดียวกัน (ทับซ้อนกัน)
ขีดจำกัดการเกิดพร้อมกันใช้แนวคิดของเซมาฟอร์เมื่อเข้าคิว และทำงานดังนี้ เมื่อมีการเข้าคิวงาน เราจะตรวจสอบว่างานนั้นระบุการควบคุมการเกิดพร้อมกันหรือไม่ หากเป็นเช่นนั้น เราจะตรวจสอบเซมาฟอร์เพื่อหาคีย์การทำงานพร้อมกันที่คำนวณได้ หากเซมาฟอร์เปิด เราจะอ้างสิทธิ์และตั้งค่างานเป็น พร้อม พร้อมหมายความว่าคนงานสามารถหยิบขึ้นมาเพื่อดำเนินการได้ เมื่องานดำเนินการเสร็จสิ้น (ไม่ว่าจะสำเร็จหรือไม่สำเร็จ ส่งผลให้การดำเนินการล้มเหลว) เราจะส่งสัญญาณสัญญาณและพยายามปลดบล็อกงานถัดไปด้วยคีย์เดียวกัน ถ้ามี การเลิกบล็อกงานถัดไปไม่ได้หมายถึงการรันงานนั้นทันที แต่ย้ายจากที่ ถูกบล็อก ไปเป็น พร้อม เนื่องจากมีบางสิ่งที่สามารถเกิดขึ้นได้ซึ่งทำให้งานแรกไม่สามารถปล่อยเซมาฟอร์และปลดบล็อกงานถัดไปได้ (เช่น มีคนดึงปลั๊กในเครื่องที่ผู้ปฏิบัติงานกำลังทำงานอยู่) เราจึงมี duration
เป็นความล้มเหลว งานที่ถูกบล็อกเป็นเวลานานกว่านั้นคือผู้สมัครที่จะได้รับการปล่อยตัว แต่จะมากเท่าที่กฎการทำงานพร้อมกันอนุญาตเท่านั้น เนื่องจากแต่ละคนจะต้องผ่านการตรวจสอบการเต้นรำสัญญาณ ซึ่งหมายความว่า duration
ไม่ได้เกี่ยวกับงานที่อยู่ในคิวหรือกำลังดำเนินการ แต่เกี่ยวกับงานที่ถูกบล็อกที่กำลังรออยู่
ตัวอย่างเช่น:
class DeliverAnnouncementToContactJob < ApplicationJob
limits_concurrency to : 2 , key : -> ( contact ) { contact . account } , duration : 5 . minutes
def perform ( contact )
# ...
โดยที่ contact
และ account
เป็นบันทึก ActiveRecord
ในกรณีนี้ เราจะตรวจสอบให้แน่ใจว่างานประเภท DeliverAnnouncementToContact
สำหรับบัญชีเดียวกันจะทำงานพร้อมกันได้สูงสุดสองงาน ไม่ว่าด้วยเหตุผลใดก็ตาม หากหนึ่งในงานเหล่านั้นใช้เวลานานกว่า 5 นาที หรือไม่ปลดล็อคการทำงานพร้อมกัน (ส่งสัญญาณสัญญาณ) ภายใน 5 นาทีหลังจากได้รับงาน งานใหม่ที่มีคีย์เดียวกันอาจได้รับการล็อค
ลองดูตัวอย่างอื่นโดยใช้ group
:
class Box :: MovePostingsByContactToDesignatedBoxJob < ApplicationJob
limits_concurrency key : -> ( contact ) { contact } , duration : 15 . minutes , group : "ContactActions"
def perform ( contact )
# ...
class Bundle :: RebundlePostingsJob < ApplicationJob
limits_concurrency key : -> ( bundle ) { bundle . contact } , duration : 15 . minutes , group : "ContactActions"
def perform ( bundle )
# ...
ในกรณีนี้ หากเรามีงาน Box::MovePostingsByContactToDesignatedBoxJob
ที่ถูกจัดคิวสำหรับเรกคอร์ดผู้ติดต่อที่มี id 123
และงาน Bundle::RebundlePostingsJob
อื่นที่จัดคิวพร้อมกันสำหรับเรกคอร์ดบันเดิลที่อ้างอิงผู้ติดต่อ 123
จะมีเพียงหนึ่งงานเท่านั้นที่จะได้รับอนุญาตให้ดำเนินการต่อ อีกอันจะถูกบล็อกจนกว่าอันแรกจะเสร็จ (หรือผ่านไป 15 นาที ไม่ว่าอะไรจะเกิดขึ้นก่อน)
โปรดทราบว่าการตั้งค่า duration
จะขึ้นอยู่กับค่าของ concurrency_maintenance_interval
ที่คุณตั้งไว้สำหรับผู้มอบหมายงานโดยอ้อม เนื่องจากนั่นจะเป็นความถี่ในการตรวจสอบและเลิกบล็อกงานที่ถูกบล็อก โดยทั่วไป คุณควรกำหนด duration
ในลักษณะที่งานทั้งหมดของคุณจะเสร็จสิ้นได้ดีภายใต้ระยะเวลานั้น และคิดว่างานบำรุงรักษาการทำงานพร้อมกันนั้นไม่ปลอดภัยในกรณีที่มีสิ่งผิดปกติเกิดขึ้น
งานจะถูกปลดบล็อคตามลำดับความสำคัญ แต่ลำดับคิวจะไม่ถูกนำมาพิจารณาในการปลดบล็อคงาน นั่นหมายความว่า หากคุณมีกลุ่มงานที่ใช้กลุ่มการทำงานพร้อมกัน แต่อยู่ในคิวที่แตกต่างกัน หรืองานในคลาสเดียวกันที่คุณเข้าคิวในคิวที่แตกต่างกัน ลำดับคิวที่คุณตั้งค่าไว้สำหรับผู้ปฏิบัติงานจะไม่ถูกนำมาพิจารณาเมื่อเลิกบล็อกที่ถูกบล็อก คน เหตุผลก็คืองานที่รันจะปลดบล็อกงานถัดไป และตัวงานเองไม่ทราบเกี่ยวกับลำดับคิวของพนักงานคนใดคนหนึ่ง (คุณอาจมีพนักงานที่แตกต่างกันซึ่งมีลำดับคิวต่างกันก็ได้) โดยจะรู้ได้เฉพาะลำดับความสำคัญเท่านั้น เมื่องานที่ถูกบล็อกถูกปลดบล็อคและพร้อมสำหรับการสำรวจแล้ว พนักงานจะเลือกงานเหล่านั้นตามลำดับคิว
สุดท้าย งานที่ล้มเหลวซึ่งถูกลองใหม่โดยอัตโนมัติหรือด้วยตนเองจะทำงานในลักษณะเดียวกับงานใหม่ที่ได้รับการจัดคิว: งานเหล่านี้จะอยู่ในคิวเพื่อรับสัญญาณแบบเปิด และเมื่อใดก็ตามที่ได้รับงาน งานเหล่านั้นจะถูกเรียกใช้ ไม่สำคัญว่าพวกเขาจะได้รับสัญญาณแบบเปิดในอดีตหรือไม่
Solid Queue ไม่มีกลไกการลองใหม่อัตโนมัติ แต่ต้องใช้ Active Job สำหรับสิ่งนี้ งานที่ล้มเหลวจะถูกเก็บไว้ในระบบ และ การดำเนินการที่ล้มเหลว (บันทึกในตาราง solid_queue_failed_executions
) จะถูกสร้างขึ้นสำหรับสิ่งเหล่านี้ งานจะอยู่ที่นั่นจนกว่าจะละทิ้งหรือจัดคิวใหม่ด้วยตนเอง คุณสามารถทำได้ในคอนโซลเป็น:
failed_execution = SolidQueue :: FailedExecution . find ( ... ) # Find the failed execution related to your job
failed_execution . error # inspect the error
failed_execution . retry # This will re-enqueue the job as if it was enqueued for the first time
failed_execution . discard # This will delete the job from the system
อย่างไรก็ตาม เราขอแนะนำให้ดูที่ mission_control-jobs ซึ่งเป็นแดชบอร์ดที่คุณสามารถตรวจสอบและลองใหม่/ทิ้งงานที่ล้มเหลวได้
บริการติดตามข้อผิดพลาดบางอย่างที่ทำงานร่วมกับ Rails เช่น Sentry หรือ Rollbar จะเชื่อมต่อกับ Active Job และรายงานข้อผิดพลาดที่ไม่ได้รับการจัดการที่เกิดขึ้นระหว่างการปฏิบัติงานโดยอัตโนมัติ อย่างไรก็ตาม หากระบบติดตามข้อผิดพลาดของคุณไม่มี หรือหากคุณต้องการการรายงานแบบกำหนดเอง คุณสามารถเชื่อมโยงกับ Active Job ได้ด้วยตัวเอง วิธีที่เป็นไปได้ในการทำเช่นนี้คือ:
# application_job.rb
class ApplicationJob < ActiveJob :: Base
rescue_from ( Exception ) do | exception |
Rails . error . report ( exception )
raise exception
end
end
โปรดทราบว่าคุณจะต้องทำซ้ำตรรกะข้างต้นใน ActionMailer::MailDeliveryJob
ด้วย นั่นเป็นเพราะว่า ActionMailer
ไม่ได้สืบทอดมาจาก ApplicationJob
แต่ใช้ ActionMailer::MailDeliveryJob
ซึ่งสืบทอดมาจาก ActiveJob::Base
แทน
# application_mailer.rb
class ApplicationMailer < ActionMailer :: Base
ActionMailer :: MailDeliveryJob . rescue_from ( Exception ) do | exception |
Rails . error . report ( exception )
raise exception
end
end
เรามีปลั๊กอิน Puma หากคุณต้องการเรียกใช้หัวหน้างานของ Solid Queue ร่วมกับ Puma และมี Puma ตรวจสอบและจัดการมัน คุณเพียงแค่ต้องเพิ่ม
plugin :solid_queue
ไปยังการกำหนดค่า puma.rb
ของคุณ
เนื่องจากสิ่งนี้อาจค่อนข้างยุ่งยากและผู้คนจำนวนมากไม่จำเป็นต้องกังวลเกี่ยวกับเรื่องนี้ โดยค่าเริ่มต้น Solid Queue จะได้รับการกำหนดค่าในฐานข้อมูลอื่นเป็นแอปหลัก การจัดคิวงานจะถูกเลื่อนออกไปจนกว่าธุรกรรมที่กำลังดำเนินอยู่จะถูกสร้างขึ้น ต้องขอบคุณ Active Job ในตัวของ Active Job ความสามารถในการทำเช่นนี้ ซึ่งหมายความว่าแม้ว่าคุณจะเรียกใช้ Solid Queue ใน DB เดียวกันกับแอปของคุณ คุณจะไม่สามารถใช้ประโยชน์จากความสมบูรณ์ของธุรกรรมนี้ได้
หากคุณต้องการเปลี่ยนแปลง คุณสามารถตั้งค่า config.active_job.enqueue_after_transaction_commit
เป็น never
ได้ คุณยังสามารถตั้งค่านี้ตามงานได้อีกด้วย
หากคุณตั้งค่าเป็น never
แต่ยังคงต้องการให้แน่ใจว่าคุณไม่ได้มีความสมบูรณ์ของธุรกรรมโดยไม่ได้ตั้งใจ คุณสามารถตรวจสอบได้ว่า:
งานของคุณที่ใช้ข้อมูลเฉพาะจะถูกจัดคิวไว้ในการเรียกกลับ after_commit
เสมอหรือจากที่ที่คุณมั่นใจว่าข้อมูลใดก็ตามที่งานจะใช้นั้นถูกส่งไปยังฐานข้อมูลก่อนที่งานจะถูกจัดคิว
หรือคุณกำหนดค่าฐานข้อมูลอื่นสำหรับ Solid Queue แม้ว่าจะเหมือนกับแอปของคุณก็ตาม เพื่อให้แน่ใจว่าการเชื่อมต่อที่แตกต่างกันในคำขอจัดการเธรดหรืองานที่กำลังรันอยู่สำหรับแอปของคุณจะถูกนำมาใช้ในการจัดคิวงาน ตัวอย่างเช่น:
class ApplicationRecord < ActiveRecord :: Base
self . abstract_class = true
connects_to database : { writing : :primary , reading : :replica }
config . solid_queue . connects_to = { database : { writing : :primary , reading : :replica } }
Solid Queue รองรับการกำหนดงานที่เกิดซ้ำซึ่งทำงานตามเวลาที่กำหนดในอนาคต เป็นประจำ เช่น งาน cron สิ่งเหล่านี้ได้รับการจัดการโดยกระบวนการกำหนดตารางเวลาและถูกกำหนดไว้ในไฟล์การกำหนดค่าของตนเอง ตามค่าเริ่มต้น ไฟล์จะอยู่ใน config/recurring.yml
แต่คุณสามารถตั้งค่าพาธอื่นได้โดยใช้ตัวแปรสภาพแวดล้อม SOLID_QUEUE_RECURRING_SCHEDULE
หรือโดยใช้ตัวเลือก --recurring_schedule_file
กับ bin/jobs
เช่นนี้
bin/jobs --recurring_schedule_file=config/schedule.yml
การกำหนดค่าเองมีลักษณะดังนี้:
production :
a_periodic_job :
class : MyJob
args : [ 42, { status: "custom_status" } ]
schedule : every second
a_cleanup_task :
command : " DeletedStuff.clear_all "
schedule : every day at 9am
งานจะถูกระบุเป็นแฮช/พจนานุกรม โดยที่คีย์จะเป็นคีย์ของงานเป็นการภายใน แต่ละงานจะต้องมี class
ซึ่งจะเป็นคลาสงานที่จะเข้าคิว หรือ command
ซึ่งจะถูกประเมินในบริบทของงาน ( SolidQueue::RecurringJob
) ที่จะถูกจัดคิวตามกำหนดเวลาใน คิว solid_queue_recurring
แต่ละงานจำเป็นต้องมีกำหนดการด้วย ซึ่งแยกวิเคราะห์โดยใช้ Fugit ดังนั้นจึงยอมรับทุกสิ่งที่ Fugit ยอมรับเป็น cron คุณสามารถเลือกจัดหาสิ่งต่อไปนี้สำหรับแต่ละงาน:
args
: อาร์กิวเมนต์ที่จะส่งไปยังงาน เป็นอาร์กิวเมนต์เดียว แฮช หรืออาร์เรย์ของอาร์กิวเมนต์ที่สามารถรวม kwargs เป็นองค์ประกอบสุดท้ายในอาร์เรย์ได้งานในการกำหนดค่าตัวอย่างด้านบนจะถูกจัดคิวทุกวินาทีเป็น:
MyJob . perform_later ( 42 , status : "custom_status" )
queue
: คิวอื่นที่จะใช้เมื่อเข้าคิวงาน หากไม่มี คิวจะถูกตั้งค่าสำหรับคลาสงาน
priority
: ค่าลำดับความสำคัญที่เป็นตัวเลขที่จะใช้เมื่อเข้าคิวงาน
งานจะถูกจัดคิวตามเวลาที่สอดคล้องกันโดยผู้จัดกำหนดการ และแต่ละงานจะจัดกำหนดการงานถัดไป สิ่งนี้ได้รับแรงบันดาลใจจากสิ่งที่ GoodJob ทำ
คุณสามารถเรียกใช้ตัวกำหนดเวลาหลายตัวด้วยการกำหนดค่า recurring_tasks
เดียวกันได้ ตัวอย่างเช่น หากคุณมีเซิร์ฟเวอร์หลายตัวสำหรับการสำรอง และคุณเรียกใช้ scheduler
มากกว่าหนึ่งเซิร์ฟเวอร์ เพื่อหลีกเลี่ยงการจัดคิวงานที่ซ้ำกันในเวลาเดียวกัน รายการในตาราง solid_queue_recurring_executions
ใหม่จะถูกสร้างขึ้นในธุรกรรมเดียวกันกับงานที่อยู่ในคิว ตารางนี้มีดัชนีเฉพาะบน task_key
และ run_at
เพื่อให้แน่ใจว่าจะสร้างเพียงรายการเดียวต่องานต่อครั้ง วิธีนี้จะใช้งานได้ก็ต่อเมื่อคุณตั้งค่า preserve_finished_jobs
เป็น true
(ค่าเริ่มต้น) และการรับประกันจะมีผลตราบเท่าที่คุณยังคงรักษางานไว้
หมายเหตุ : รองรับกำหนดการที่เกิดซ้ำเพียงรายการเดียว ดังนั้นคุณจึงสามารถมีตัวกำหนดเวลาหลายตัวโดยใช้กำหนดการเดียวกันได้ แต่จะไม่สามารถใช้ตัวกำหนดเวลาหลายตัวที่ใช้การกำหนดค่าต่างกันได้
ท้ายที่สุด คุณสามารถกำหนดค่างานที่ไม่ได้รับการจัดการโดย Solid Queue ได้ นั่นคือคุณสามารถมีงานเช่นนี้ในแอปของคุณ:
class MyResqueJob < ApplicationJob
self . queue_adapter = :resque
def perform ( arg )
# ..
end
end
คุณยังสามารถกำหนดค่านี้ได้ใน Solid Queue:
my_periodic_resque_job :
class : MyResqueJob
args : 22
schedule : " */5 * * * * "
และงานจะถูกจัดคิวผ่าน perform_later
ดังนั้นงานจะรันใน Resque อย่างไรก็ตาม ในกรณีนี้ เราจะไม่ติดตามบันทึก solid_queue_recurring_execution
ใดๆ และจะไม่รับประกันใดๆ ว่างานจะถูกจัดคิวเพียงครั้งเดียวในแต่ละครั้ง
Solid Queue ได้รับแรงบันดาลใจจาก Resque และ GoodJob เราขอแนะนำให้ตรวจสอบโครงการเหล่านี้เนื่องจากเป็นตัวอย่างที่ดีที่เราได้เรียนรู้มากมาย
อัญมณีนี้มีให้ใช้งานในรูปแบบโอเพ่นซอร์สภายใต้เงื่อนไขของใบอนุญาต MIT