यह एक अच्छा सवाल है जिसकी तह तक जाना है।
जब आप ऐसा करते हैं:
verifier(3,4).then(...)
यह एक नया वादा देता है जिसे इवेंट लूप में एक और चक्र वापस करने की आवश्यकता होती है, इससे पहले कि नया अस्वीकृत वादा .catch()
हैंडलर को चला सकता है। वह अतिरिक्त चक्र अगला क्रम देता है:
verifier(5,4).then(...)
.then()
पिछली पंक्ति से पहले अपने हैंडलर को चलाने का मौका .catch()
क्योंकि यह पहले से ही कतार में पहले .catch()
से कतार में था और आइटम एफआईएफओ क्रम में कतार से चलाए जाते हैं।
ध्यान दें, कि यदि आप .then(f1, f2)
फॉर्म का उपयोग करते हैं .then().catch()
, तो यह तब चलता है जब आप इसकी अपेक्षा करते हैं, क्योंकि कोई अतिरिक्त वादा नहीं है और इस प्रकार कोई टिक नहीं है:
const verifier = (a, b) =>
new Promise((resolve, reject) => (a > b ? resolve(true) : reject(false)));
verifier(3, 4)
.then((response) => console.log("response (3,4): ", response),
(error) => console.log("error (3,4): ", error)
);
verifier(5, 4)
.then((response) => console.log("response (5,4): ", response))
.catch((error) => console.log("error (5,4): ", error));
ध्यान दें, मैंने सभी संदेशों को भी लेबल किया है ताकि आप देख सकें कि verifier()
वे किस कॉल से आते हैं जिससे आउटपुट को पढ़ना बहुत आसान हो जाता है।
ईएस 6 स्पेक कॉलबैक ऑर्डर और अधिक विस्तृत विवरण पर कल्पना
ईएस 6 कल्पना हमें बताती है कि "जॉब" का वादा करें (जैसा कि यह कॉलबैक से .then()
या कॉल करता है .catch()
) एफआईएफओ ऑर्डर में चलाए जाते हैं, जब उन्हें नौकरी की कतार में डाला जाता है। यह विशेष रूप से FIFO का नाम नहीं लेता है, लेकिन यह निर्दिष्ट करता है कि नई नौकरियां कतार के अंत में डाली जाती हैं और कतार की शुरुआत से नौकरियां चलती हैं। कि FIFO आदेश को लागू करता है।
PerformPromiseThen (जिसमें से कॉलबैक निष्पादित होता है .then()
) EnqueueJob को बढ़ावा देगा जो कि हैंडलर को हल या अस्वीकार करने के लिए वास्तव में चलाने के लिए शेड्यूल किया जाता है। EnqueueJob निर्दिष्ट करता है कि लंबित कार्य को नौकरी की कतार में सबसे पीछे जोड़ा जाता है। तब NextJob ऑपरेशन कतार के सामने से आइटम खींचता है। यह वादा नौकरी कतार से नौकरियों की सेवा में FIFO आदेश सुनिश्चित करता है।
इसलिए, मूल प्रश्न में उदाहरण में, हम verifier(3,4)
वादे के लिए कॉलबैक प्राप्त करते हैं और verifier(5,4)
वादे को उस क्रम में नौकरी की कतार में डाल दिया जाता है, क्योंकि वे दोनों मूल वादे किए जाते हैं। फिर, जब दुभाषिया ईवेंट लूप में वापस जाता है, तो वह पहले verifier(3,4)
काम चुनता है । यह वादा खारिज कर दिया गया है और इसमें उसके लिए कोई कॉलबैक नहीं है verifier(3,4).then(...)
। तो, यह क्या करता है कि verifier(3,4).then(...)
वापस आए वादे को अस्वीकार कर देता है और इससे verifier(3,4).then(...).catch(...)
हैंडलर को जॉबक्यू में डाला जाता है।
फिर, यह इवेंट लूप पर वापस जाता है और अगली नौकरी जो इसे जॉब क्यू से खींचती है वह है verifier(5, 4)
जॉब। इसका एक हल किया हुआ वादा और एक संकल्प हैंडलर है, इसलिए यह उस हैंडलर को बुलाता है। यह response (5,4):
आउटपुट दिखाए जाने का कारण बनता है।
फिर, यह ईवेंट लूप पर वापस जाता है और अगली नौकरी जो इसे जॉब क्यू से खींचती है वह वह verifier(3,4).then(...).catch(...)
कार्य है जहां यह चलता है और इसके कारण error (3,4)
आउटपुट दिखाया जाता है।
ऐसा इसलिए है क्योंकि .catch()
1 श्रृंखला .then()
में 2 श्रृंखला की तुलना में इसकी श्रृंखला में एक वादा स्तर गहरा है जो आपके द्वारा रिपोर्ट किए गए आदेश का कारण बनता है। और, यह इसलिए है क्योंकि वादा श्रृंखला एक स्तर से अगले तक FIFO क्रम में नौकरी की कतार के माध्यम से निकाली जाती है, समकालिक रूप से नहीं।
निर्धारण स्तर के इस स्तर पर भरोसा करने के बारे में सामान्य सिफारिश
FYI करें, सामान्य तौर पर, मैं कोड लिखने की कोशिश करता हूं जो विस्तृत समय ज्ञान के इस स्तर पर निर्भर नहीं करता है। हालांकि यह जानने के लिए उत्सुक और कभी-कभार उपयोगी होता है, यह एक नाजुक कोड होता है क्योंकि कोड के लिए एक सरल रूप से सहज परिवर्तन के कारण रिश्तेदार समय में बदलाव हो सकता है। इसलिए, अगर इस तरह से दो श्रृंखलाओं के बीच समय महत्वपूर्ण है, तो मैं कोड को इस तरह से लिखना चाहूंगा जो समय को उस तरह से मजबूर करता है जैसा कि मैं चाहता हूं कि इस विस्तृत समझ के स्तर पर भरोसा करने के बजाय।