लारवेल कतारों के साथ हमारे उत्पाद को तैयार करना

विशेष रूप से "फ्रेमवर्क लारवेल" पाठ्यक्रम के छात्रों के लिए लेख का अनुवाद तैयार किया गया था




नमस्ते, मैं Valerio हूँ, इटली के एक सॉफ्टवेयर इंजीनियर।

यह गाइड उन सभी PHP डेवलपर्स के लिए है, जिनके पास पहले से ही वास्तविक उपयोगकर्ताओं के साथ ऑनलाइन आवेदन हैं, लेकिन जिनके पास लारवेल कतारों का उपयोग करके अपने सिस्टम में स्केलेबिलिटी को लागू करने (या बेहतर ढंग से सुधारने) की गहरी समझ का अभाव है। मैंने पहली बार लारवेल के बारे में 2013 के अंत में फ्रेमवर्क के 5 वें संस्करण की शुरुआत में सीखा था। तब मैं अभी तक गंभीर परियोजनाओं में शामिल एक डेवलपर नहीं था, और आधुनिक फ्रेमवर्क के पहलुओं में से एक, विशेष रूप से लारवेल में, जो मुझे सबसे अयोग्य लग रहा था, क्यू थे।

दस्तावेज़ीकरण को पढ़ते हुए, मैंने क्षमता के बारे में अनुमान लगाया, लेकिन वास्तविक विकास के अनुभव के बिना, यह सब केवल मेरे दिमाग में सिद्धांतों के स्तर पर बना रहा।
आज, मैं निर्माता हूं Inspector.dev- रियलटाइम डैशबोर्ड , जो हर घंटे हजारों कार्य करता है, और मैं इस वास्तुकला को पहले से बहुत बेहतर समझता हूं।



इस लेख में मैं आपको बताने जा रहा हूं कि कैसे मैंने कतार और कार्यों की खोज की और क्या विन्यास ने मुझे सर्वर संसाधनों की बचत करते हुए वास्तविक समय में बड़ी मात्रा में डेटा को संसाधित करने में मदद की।

परिचय


जब एक PHP आवेदन एक आने वाली http अनुरोध प्राप्त करता है, तो हमारे कोड को क्रमिक रूप से चरणबद्ध तरीके से निष्पादित किया जाता है जब तक कि अनुरोध पूरा नहीं हो जाता है और ग्राहक को एक प्रतिक्रिया दी जाती है (उदाहरण के लिए, उपयोगकर्ता का ब्राउज़र)। यह तुल्यकालिक व्यवहार वास्तव में सहज, पूर्वानुमान योग्य और समझने में आसान है। मैं समापन बिंदु के लिए एक HTTP अनुरोध भेजता हूं, एप्लिकेशन डेटाबेस से डेटा निकालता है, इसे उपयुक्त प्रारूप में परिवर्तित करता है, कुछ अतिरिक्त कार्य करता है और उन्हें वापस भेजता है। सब कुछ रैखिक रूप से होता है।

कार्य और कतार अतुल्यकालिक व्यवहार का परिचय देते हैं जो इस लाइन प्रवाह का उल्लंघन करता है। इसलिए ये विशेषताएँ मुझे पहली बार में थोड़ी अजीब लगीं।
लेकिन कभी-कभी एक आने वाली http अनुरोध समय लेने वाली कार्यों का एक चक्र ट्रिगर कर सकता है, उदाहरण के लिए, सभी टीम के सदस्यों को ईमेल सूचनाएं भेजना। इसका मतलब यह हो सकता है कि आप छह या दस ईमेल भेज सकते हैं, जिसमें चार या पाँच सेकंड लग सकते हैं। इसलिए, हर बार जब उपयोगकर्ता संबंधित बटन पर क्लिक करता है, तो उसे एप्लिकेशन का उपयोग जारी रखने से पहले पांच सेकंड इंतजार करना होगा।

आवेदन जितना बढ़ता है, यह समस्या उतनी ही खराब होती जाती है।

एक कार्य क्या है?


एक नौकरी एक वर्ग है जो उस हैंडल पद्धति को लागू करता है जिसमें तर्क शामिल हैं जिसे हम अतुल्यकालिक रूप से निष्पादित करना चाहते हैं।

<?php

use Illuminate\Contracts\Queue\ShouldQueue;
use Illuminate\Foundation\Bus\Dispatchable;
use Illuminate\Queue\InteractsWithQueue;
use Illuminate\Bus\Queueable;


class CallExternalAPI implements ShouldQueue
{
    use Dispatchable,
        InteractsWithQueue,
        Queueable;
        
    /**
     * @var string
     */
    protected $url;

    /**
     *    .
     *
     * @param array $Data
     */
    public function __construct($url)
    {
        $this->url = $url;
    }
    

    /**
     *  ,   .
     *
     * @return void
     * @throws \Throwable
     */
    public function handle()
    {
        file_get_contents($this->url);
    }
}

जैसा कि ऊपर उल्लेख किया गया है, नौकरी में कोड के एक टुकड़े के समापन का मुख्य कारण उपयोगकर्ता को इसे पूरा करने के लिए इंतजार किए बिना समय लेने वाले कार्य को पूरा करना है।

"श्रमसाध्य कार्यों" से हमारा क्या तात्पर्य है?


यह एक स्वाभाविक प्रश्न है। ईमेल भेजना उन लेखों में सबसे आम उदाहरण है जिसका उपयोग कतारों के बारे में किया जाता है, लेकिन मैं आपको वास्तविक अनुभव के बारे में बताना चाहता हूं कि मुझे क्या करने की आवश्यकता है।

एक उत्पाद स्वामी के रूप में, हमारे लिए हमारे मार्केटिंग और ग्राहक सहायता टूल के साथ उपयोगकर्ता की यात्रा की जानकारी को सिंक्रनाइज़ करना बहुत महत्वपूर्ण है। इस प्रकार, उपयोगकर्ता कार्यों के आधार पर, हम सेवा और विपणन उद्देश्यों के लिए एपीआई (या बाहरी http कॉल) के माध्यम से विभिन्न बाहरी सॉफ़्टवेयर में उपयोगकर्ता जानकारी को अपडेट करते हैं।
मेरे आवेदन में सबसे अधिक उपयोग किए जाने वाले समापन बिंदुओं में से एक 10 ईमेल भेज सकता है और पूरा होने से पहले बाहरी सेवाओं में 3 http कॉल कर सकता है। कोई भी उपयोगकर्ता इतना समय इंतजार नहीं करेगा - सबसे अधिक संभावना है, वे सभी बस मेरे आवेदन का उपयोग करना बंद कर देते हैं।

कतारों के लिए धन्यवाद, मैं आवंटित कक्षाओं में इन सभी कार्यों को संलग्न कर सकता हूं, निर्माणकर्ता को उनके काम के निष्पादन के लिए आवश्यक जानकारी को स्थानांतरित कर सकता हूं, और उन्हें पृष्ठभूमि में बाद की तारीख में पूरा करने के लिए शेड्यूल कर सकता हूं ताकि मेरे नियंत्रक तुरंत जवाब वापस कर सकें।

<?php

class ProjectController 
{
    public function store(Request $request)
    {
        $project = Project::create($request->all());
        
        //  NotifyMembers, TagUserActive, NotifyToProveSource 
        //   ,     
        Notification::queue(new NotifyMembers($project->owners));
        $this->dispatch(new TagUserAsActive($project->owners));
        $this->dispatch(new NotifyToProveSource($project->owners));
        
        return $project;
    }
}

जवाब वापस करने से पहले मुझे इन सभी प्रक्रियाओं के पूरा होने की प्रतीक्षा करने की आवश्यकता नहीं है; इसके विपरीत, प्रतीक्षा उन्हें कतार में प्रकाशित करने के लिए आवश्यक समय के बराबर होगी। और इसका मतलब है कि 10 सेकंड और 10 मिली सेकंड के बीच का अंतर !!!

कतार में भेजने के बाद ये कार्य कौन करता है?


यह क्लासिक प्रकाशक / उपभोक्ता वास्तुकला है हमने अपने कार्यों को पहले ही कंट्रोलर से कतार में प्रकाशित किया है, अब हम यह समझने जा रहे हैं कि कतार का उपयोग कैसे किया जाता है, और आखिरकार, कार्य किए जाते हैं।



कतार का उपयोग करने के लिए, हमें सबसे लोकप्रिय कारीगरों में से एक को चलाने की आवश्यकता है:

php artisan queue:work

जैसा कि प्रलेखन कहता है:
लारवेल में एक कतार कार्यकर्ता शामिल होता है जो कतारबद्ध होने पर नए कार्यों को संसाधित करता है।

महान! लारवेल कतार के कार्यों के लिए तैयार-तैयार इंटरफ़ेस और कतार से कार्यों को प्राप्त करने और पृष्ठभूमि में उनके कोड को निष्पादित करने के लिए तैयार-से-उपयोग आदेश प्रदान करता है।

पर्यवेक्षक की भूमिका


यह शुरुआत में एक और "अजीब बात" थी। मुझे लगता है कि नई चीजों की खोज करना सामान्य है। प्रशिक्षण के इस चरण के बाद, मैं इन लेखों को अपने कौशल को व्यवस्थित करने में मदद करने के लिए लिखता हूं, और साथ ही अन्य डेवलपर्स को अपने ज्ञान का विस्तार करने में मदद करता हूं।

यदि अपवाद को फेंकने के दौरान कार्य विफल हो जाता है, तो टीम queue:workअपना काम रोक देगी

एक प्रक्रिया queue:workको लगातार चलाने के लिए (अपनी कतारों का उपभोग करते हुए), आपको सुपरवाइज़र जैसी प्रक्रिया मॉनिटर का उपयोग करना चाहिए ताकि यह सुनिश्चित किया जा सके कि कमांड queue:workकाम करना बंद नहीं करता है भले ही कार्य एक अपवाद फेंकता है। पर्यवेक्षक क्रैश होने के बाद कमांड को पुनरारंभ करता है, शुरू करना। अगले कार्य से फिर से, फेंकने वाले अपवाद को अलग करना।

कार्य आपके सर्वर पर पृष्ठभूमि में चलेगा, अब HTTP अनुरोध पर निर्भर नहीं होगा। यह कुछ परिवर्तनों का परिचय देता है जिन्हें मुझे कार्य कोड को लागू करते समय विचार करना था।

यहाँ सबसे महत्वपूर्ण हैं जिन पर मैं ध्यान दूंगा:

मुझे कैसे पता चलेगा कि कार्य कोड काम नहीं कर रहा है?


जब पृष्ठभूमि में चल रहा है, तो आप तुरंत नोटिस नहीं कर सकते कि आपका कार्य त्रुटियों का कारण बन रहा है।
अब आपके पास तत्काल प्रतिक्रिया नहीं होगी, जैसे कि आपके ब्राउज़र से http अनुरोध करते समय। यदि कार्य विफल हो जाता है, तो यह चुपचाप करेगा और कोई भी नोटिस नहीं करेगा। हर दोष को धरातल पर उतारने के

लिए इंस्पेक्टर जैसे एक रीयल-टाइम मॉनिटरिंग टूल को एकीकृत करने पर विचार करें

आपके पास http अनुरोध नहीं है


अधिक HTTP अनुरोध नहीं है। आपका कोड cli से निष्पादित किया जाएगा।

यदि आपको अपने कार्यों को पूरा करने के लिए क्वेरी पैरामीटर की आवश्यकता है, तो आपको रनटाइम पर बाद में उपयोग के लिए उन्हें कार्य निर्माता को पास करना होगा:

<?php

//   

class TagUserJob implements ShouldQueue
{
    public $data;
    
    public function __construct(array $data)
    {
        $this->data = $data;
    }
}

//       

$this->dispatch(new TagUserJob($request->all()));

आप नहीं जानते कि किसने लॉग इन किया है


अब कोई सत्र नहीं हैउसी तरह, आप उस उपयोगकर्ता की पहचान नहीं जान पाएंगे जो लॉग इन है, इसलिए यदि आपको कार्य को पूरा करने के लिए उपयोगकर्ता के बारे में जानकारी चाहिए, तो आपको उपयोगकर्ता को कार्य निर्माता को पास करने की आवश्यकता है:

<?php

//   
class TagUserJob implements ShouldQueue
{
    public $user;
    
    public function __construct(User $user)
    {
        $this->user= $user;
    }
}

//       
$this->dispatch(new TagUserJob($request->user()));

पैमाने कैसे समझें


दुर्भाग्य से, कई मामलों में यह पर्याप्त नहीं है। एक लाइन और एक उपभोक्ता का उपयोग करना जल्द ही बेकार हो सकता है।

कतार फीफो बफ़र हैं ("पहले में, पहले बाहर")। यदि आपने बहुत से कार्यों की योजना बनाई है, तो शायद विभिन्न प्रकारों की भी, उन्हें पूरा करने से पहले अपने कार्यों को पूरा करने के लिए दूसरों की प्रतीक्षा करनी होगी।

स्केल करने के दो तरीके हैं:

प्रति कतार कई उपभोक्ता।



इस प्रकार, कतार से पांच कार्यों को एक बार में हटा दिया जाएगा, जिससे कतार प्रसंस्करण तेज हो जाएगा।

विशेष-उद्देश्य कतारें

आप प्रत्येक कतार के लिए समर्पित उपभोक्ता के साथ लॉन्च किए जाने वाले प्रत्येक प्रकार के कार्य के लिए विशिष्ट कतार भी बना सकते हैं।



इस प्रकार, प्रत्येक कतार को स्वतंत्र रूप से संसाधित किया जाएगा, बिना अन्य प्रकार के कार्यों की प्रतीक्षा के।

क्षितिज


लारवेल होरिजन एक कतार प्रबंधक है जो आपको इस बात पर पूरा नियंत्रण देता है कि आप कितनी कतारें स्थापित करना चाहते हैं, और उपभोक्ताओं को व्यवस्थित करने की क्षमता, डेवलपर्स को इन दो रणनीतियों को संयोजित करने और आपकी स्केलेबिलिटी की जरूरतों को पूरा करने वाले को लागू करने की अनुमति देता है।

प्रक्षेपण php कारीगर कतार के बजाय php कारीगर क्षितिज के माध्यम से होता है : काम । यह आदेश आपकी कॉन्फ़िगरेशन फ़ाइल को स्कैन horizon.phpकरता है और कॉन्फ़िगरेशन के आधार पर कतार के कर्मचारियों की एक श्रृंखला शुरू करता है:

<?php

'production' => [
    'supervisor-1' => [
        'connection' => "redis",
        'queue' => ['adveritisement', 'logs', 'phones'],
        'processes' => 9,
        'tries' => 3,
        'balance' => 'simple', //   simple, auto  null

    ]
]

उपरोक्त उदाहरण में, क्षितिज प्रत्येक कतार को संसाधित करने के लिए तीन प्रक्रियाओं के साथ तीन कतारें शुरू करेगा। जैसा कि लारवेल प्रलेखन में उल्लेख किया गया है, क्षितिज का कोड-संचालित दृष्टिकोण मेरे कॉन्फ़िगरेशन को एक संस्करण नियंत्रण प्रणाली में रहने की अनुमति देता है जहां मेरी टीम सहयोग कर सकती है। यह एक CI उपकरण का उपयोग करके सही समाधान है।

कॉन्फ़िगरेशन मापदंडों के अर्थ को विस्तार से जानने के लिए, इस अद्भुत लेख को पढ़ें

मेरा अपना विन्यास



<?php

'production' => [
    'supervisor-1' => [
        'connection' => 'redis',
        'queue' => ['default', 'ingest', 'notifications'],
        'balance' => 'auto',
        'processes' => 15,
        'tries' => 3,
    ],
]

निरीक्षक मुख्य रूप से तीन कतारों का उपयोग करता है:

  • बाहरी अनुप्रयोगों से डेटा का विश्लेषण करने के लिए प्रक्रियाओं के लिए निगलना;
  • यदि डेटा प्राप्त करते समय कोई त्रुटि पाई जाती है, तो सूचनाओं को तुरंत शेड्यूल करने के लिए सूचनाओं का उपयोग किया जाता है;
  • डिफ़ॉल्ट का उपयोग अन्य कार्यों के लिए किया जाता है जो मैं निगलना और सूचना प्रक्रियाओं के साथ मिश्रण नहीं करना चाहता

balance=autoक्षितिज के उपयोग के माध्यम से , वह समझता है कि सक्रिय प्रक्रियाओं की अधिकतम संख्या 15 है, जो कि कतारों के लोडिंग के आधार पर गतिशील रूप से वितरित की जाएगी।

यदि कतारें खाली हैं, तो क्षितिज प्रत्येक कतार के लिए एक सक्रिय प्रक्रिया का समर्थन करता है, जो उपभोक्ता को एक कार्य निर्धारित होने पर तुरंत कतार को संसाधित करने की अनुमति देता है।

टिप्पणियों को छोड़कर


समवर्ती पृष्ठभूमि निष्पादन कई अन्य अप्रत्याशित त्रुटियों का कारण बन सकता है, जैसे कि MySQL "लॉक आउट आउट" और कई अन्य डिज़ाइन समस्याएं। और अधिक पढ़ें यहाँ

मुझे उम्मीद है कि इस लेख ने आपको अधिक आत्मविश्वास के साथ कतारों और कार्यों का उपयोग करने में मदद की है। यदि आप हमारे बारे में अधिक जानना चाहते हैं, तो www.inspector.dev पर हमारी वेबसाइट पर जाएँ

। यहाँ प्रकाशित www.inspector.dev/what-worked-for-me-use-laravel-queues-from-the-basics-to -horizon



पाठ्यक्रम पर जाएं और छूट प्राप्त करें।



All Articles