Rust के लिए कार्य कतारें: टूल्स और लाइब्रेरी का अवलोकन
\nRust एक सिस्टम प्रोग्रामिंग भाषा है जिसका उपयोग उच्च-लोड वाली वेब सेवाओं और माइक्रोसर्विसेज बनाने के लिए तेजी से किया जा रहा है। ऐसी परियोजनाओं में प्रमुख कार्यों में से एक कतारों का उपयोग करके कार्यों का अतुल्यकालिक प्रसंस्करण आयोजित करना है। इस लेख में, हम Rust में कार्य कतारों के साथ काम करने के लिए मुख्य लाइब्रेरी और दृष्टिकोणों पर विचार करेंगे, जिसमें अंतर्निहित तंत्र और लोकप्रिय संदेश ब्रोकरों के साथ एकीकरण शामिल है।
\n\nकार्य कतारों की आवश्यकता क्यों है?
\nकार्य कतारें (task queues) लंबे या पृष्ठभूमि संचालन को अनुरोध प्रसंस्करण के मुख्य प्रवाह से अलग करने की अनुमति देती हैं। विशिष्ट उपयोग परिदृश्य:
\n- \n
- ईमेल सूचनाएं भेजना \n
- छवियों और वीडियो का प्रसंस्करण \n
- आवधिक कार्यों का निष्पादन (cron कार्य) \n
- वितरित गणनाएं \n
Rust पारिस्थितिकी तंत्र में इन उद्देश्यों के लिए कई दृष्टिकोण मौजूद हैं: अंतर्निहित अतुल्यकालिक runtime के उपयोग से लेकर बाहरी ब्रोकरों के साथ एकीकरण तक।
\n\n1. Tokio + async-std: अतुल्यकालिकता का आधार
\nविशिष्ट कतारों के बारे में बात करने से पहले, Rust में दो मुख्य अतुल्यकालिक runtime का उल्लेख करना उचित है: Tokio और async-std। वे कार्यों के साथ काम करने के लिए बुनियादी तंत्र प्रदान करते हैं:
\n- \n
tokio::spawn— पृष्ठभूमि कार्य प्रारंभ करना \n async_std::task::spawn— async-std के लिए एनालॉग \n - कार्यों के बीच संदेश स्थानांतरित करने के लिए चैनल (channels) \n
Tokio चैनलों पर एक सरल कतार का उदाहरण:
\nuse tokio::sync::mpsc;\nuse tokio::time::{sleep, Duration};\n\n#[tokio::main]\nasync fn main() {\n let (tx, mut rx) = mpsc::channel::<String>(32);\n\n // कार्य भेजें\n tokio::spawn(async move {\n for i in 0..5 {\n tx.send(format!("कार्य {}", i)).await.unwrap();\n sleep(Duration::from_millis(100)).await;\n }\n });\n\n // कार्यों को संसाधित करें\n while let Some(task) = rx.recv().await {\n println!("संसाधित कर रहा हूँ: {}", task);\n }\n}\nयह दृष्टिकोण सरल मामलों के लिए उपयुक्त है, लेकिन इसमें प्रक्रियाओं के बीच स्थायित्व और स्केलिंग का अभाव है।
\n\n2. lapin — RabbitMQ के लिए AMQP क्लाइंट
\nlapin Rust में RabbitMQ के साथ काम करने के लिए सबसे लोकप्रिय लाइब्रेरी में से एक है। यह AMQP 0-9-1 की पूरी सुविधाओं का समर्थन करता है:
\n- \n
- कतारें, एक्सचेंजर्स (exchanges), बाइंडिंग्स (bindings)
- डिलीवरी पुष्टिकरण (publisher confirms)
- डेड लेटर एक्सचेंज (dead letter exchanges)
- संदेशों की अतुल्यकालिक खपत
संदेश प्रकाशन और खपत का उदाहरण:
\nuse lapin::{options::*, types::FieldTable, Connection, ConnectionProperties};\nuse futures_util::stream::StreamExt;\n\n#[tokio::main]\nasync fn main() -> Result<(), Box<dyn std::error::Error>> {\n let conn = Connection::connect(\n "amqp://guest:guest@localhost:5672",\n ConnectionProperties::default(),\n ).await?;\n\n let channel = conn.create_channel().await?;\n channel.queue_declare(\n "task_queue",\n QueueDeclareOptions::default(),\n FieldTable::default(),\n ).await?;\n\n // कार्य प्रकाशित करें\n channel.basic_publish(\n "",\n "task_queue",\n BasicPublishOptions::default(),\n b"Hello, RabbitMQ!",\n BasicProperties::default(),\n ).await?;\n\n // कार्यों की खपत\n let mut consumer = channel.basic_consume(\n "task_queue",\n "consumer",\n BasicConsumeOptions::default(),\n FieldTable::default(),\n ).await?;\n\n while let Some(delivery) = consumer.next().await {\n let delivery = delivery?;\n println!("प्राप्त: {:?}", delivery.data);\n delivery.ack(BasicAckOptions::default()).await?;\n }\n Ok(())\n}\nlapin सक्रिय रूप से समर्थित है और अच्छी तरह से दस्तावेजीकृत है।