प्रॉम्प्ट और संदर्भ
एक idempotent रीड API में p99 अधिक है जबकि p50 सामान्य है; धीमी कॉल्स कभी-कभार होने वाली कतार (queueing) या होस्ट की अस्थायी समस्याओं के कारण प्रतीत होती हैं। रिक्वेस्ट हेजिंग डिज़ाइन करें: एक प्राइमरी भेजें, देरी के बाद दूसरे रेप्लिका को एक कॉपी जारी करें, पहला स्वीकार्य परिणाम लौटाएं, और दूसरे को रद्द करें। लागत और विफलता-प्रवर्धन (failure-amplification) की सीमाओं को समझाएं।
इंटरव्यूअर क्या टेस्ट कर रहा है
लक्ष्य को समझना
हेजिंग का लक्ष्य टेल लेटेंसी होता है; यह हर अनुरोध को तेज़ नहीं बनाता है। यह सुरक्षित रूप से दोहराए जाने योग्य रीड्स के लिए उपयुक्त है और इसे साइड-इफेक्ट वाले राइट्स को आँख बंद करके डुप्लिकेट नहीं करना चाहिए।
लागत को नियंत्रित करना
प्रत्येक अनुरोध को डुप्लिकेट करने से बैकएंड लोड लगभग दोगुना हो सकता है। एक मजबूत डिज़ाइन में विलंबित ट्रिगर, अधिकतम प्रयास गणना, थ्रॉटलिंग, कैंसिलेशन और मूल अनुरोध पर आधारित मेट्रिक्स का उपयोग किया जाता है।
सहसंबद्ध विफलताओं (Correlated Failures) को संभालना
एक ही ओवरलोड होस्ट पर दोनों प्रयास भेजने का बहुत कम लाभ है। क्रॉस-इंस्टेंस, ज़ोन, या विफलता-डोमेन रूटिंग के साथ-साथ कतार और त्रुटि सुरक्षा यह निर्धारित करती है कि हेजिंग सुरक्षित है या नहीं।
पहले स्पष्ट करने योग्य प्रश्न
- क्या API idempotent है, और क्या एकाधिक समवर्ती रीड्स स्वीकार किए जा सकते हैं?
- p50, p95, p99, p99.9 बेसलाइन और SLO क्या हैं?
- क्या धीमी कॉल्स अलग-थलग पड़े स्ट्रैग्लर (stragglers) हैं या हर रेप्लिका द्वारा साझा की जाने वाली कतारबद्ध समस्या है?
- इंस्टेंस, ज़ोन और संस्करणों में रेप्लिका का चयन कैसे किया जाता है?
- क्या कैंसिलेशन वास्तव में डाउनस्ट्रीम थ्रेड्स, कनेक्शन और कंप्यूट को मुक्त करता है?
- कौन सी त्रुटि दर, कतार की गहराई, या हेज फायर दर नीति को अक्षम करती है?
30-सेकंड का उत्तर
"मैं केवल idempotent रीड्स के लिए हेजिंग सक्षम करूँगा। पहले प्राइमरी भेजें; प्रति अनुरोध वर्ग एक गतिशील p95-शैली थ्रेशोल्ड का उपयोग करें, फिर किसी अन्य विफलता डोमेन में एक स्वस्थ रेप्लिका को एक हेज केवल तभी भेजें जब थ्रेशोल्ड समाप्त हो जाए और बजट इसकी अनुमति दे। एक समय सीमा (deadline) साझा करें, पहली सफलता लौटाएं, और हारने वाले प्रयास को रद्द करें। प्रयासों को सीमित करें, थ्रॉटलिंग और कतार/त्रुटि गार्ड का उपयोग करें, और p99, फायर दर, अतिरिक्त अनुरोध, कैंसिलेशन सफलता और मूल लेटेंसी की निगरानी करें। जब यह लोड को बढ़ाए तो नीति को अक्षम करें।"
चरण-दर-चरण विस्तृत उत्तर
अनुरोध स्टेट मशीन को परिभाषित करें
अवस्थाएं primary_sent, hedge_waiting, hedge_sent, winner_selected, और deadline_exceeded हैं। पहले प्राइमरी भेजें; यदि यह थ्रेशोल्ड के भीतर वापस आता है तो समाप्त करें, अन्यथा एक हेज बनाएं। पहली सफल प्रतिक्रिया जीतती है और अन्य सभी प्रयासों को कैंसिलेशन प्राप्त होता है।
थ्रेशोल्ड और दायरा चुनें
मेथड, टेनेंट, अनुरोध आकार, या प्रॉम्प्ट लंबाई द्वारा बकेट किए गए लेटेंसी हिस्टोग्राम बनाए रखें। सीमाओं और कोल्ड-स्टार्ट फ़ॉलबैक के साथ गतिशील p95-शैली थ्रेशोल्ड का उपयोग करें। केवल वैश्विक माध्य का उपयोग न करें या प्रत्येक अनुरोध को तुरंत डुप्लिकेट न करें।
एक स्वतंत्र रेप्लिका पर रूट करें
प्राइमरी के होस्ट, ज़ोन, या विफलता डोमेन से बचें। छोटी कतार वाले स्वस्थ नोड को प्राथमिकता दें। यदि प्रत्येक उम्मीदवार ओवरलोड है, तो हेजिंग भीड़ (congestion) को बढ़ाती है; इसके बजाय प्रतीक्षा करें, डिग्रेड करें, या तेज़ी से विफल (fail fast) हों।
कैंसिलेशन और डेडलाइन को संभालें
क्लाइंट और प्रॉक्सी को एक कैंसिलेशन टोकन का प्रसार करना चाहिए। डाउनस्ट्रीम काम को रुकना चाहिए और कनेक्शन, थ्रेड, GPU या कैश को छोड़ना चाहिए। दोनों प्रयास कुल समय सीमा साझा करते हैं ताकि डुप्लिकेटिंग उपयोगकर्ता-दृश्यमान प्रतीक्षा को न बढ़ाए।
डाउनस्ट्रीम क्षमता को सुरक्षित रखें
maxAttempts, एक न्यूनतम हेज विलंब, एक इन-फ़्लाइट बजट, और प्रति-सेवा टोकन बकेट सेट करें। gRPC maxAttempts को 5 पर सीमित करता है और पुनरुपयोग (retry) थ्रॉटलिंग प्रदान करता है; एक प्रोडक्शन डिज़ाइन को अभी भी अपनी स्वयं की क्षमता और त्रुटि बजट की आवश्यकता होती है।
त्रुटियों और गैर-idempotent कॉल्स को संभालें
केवल पुन: प्रयास करने योग्य (retryable), idempotent मामलों के लिए जारी रखें। नियतात्मक (deterministic) सत्यापन या प्रमाणीकरण त्रुटियों को तुरंत लौटाएं। राइट्स के लिए idempotency कुंजियों और डिडुप्लीकेशन की आवश्यकता होती है, या एक अनुरोध के साथ क्षतिपूर्ति का उपयोग करना चाहिए।
स्यूडोकोड
~~~text send(primary) timer = hedgeThreshold(request_class) if primary unfinished at timer and budget_allows(): send(hedge, differentfailuredomain) winner = firstsuccessbefore_deadline() cancel(allotherattempts) record(primarylatency, hedgefired, winner, cancel_result) ~~~
जटिलता, ऑब्ज़र्वेबिलिटी और रोलबैक
सबसे खराब प्रयास गणना maxAttempts द्वारा बंधी है; अतिरिक्त अनुरोध मात्रा फायर दर और कैंसिलेशन लेटेंसी पर निर्भर करती है। p50/p95/p99, हेज फायर दर, अतिरिक्त QPS, डाउनस्ट्रीम कतार, त्रुटियां, कैंसिलेशन सफलता और मूल प्राइमरी लेटेंसी को ट्रैक करें। भीड़ या त्रुटियां बढ़ने पर सेवा, टेनेंट या क्षेत्र के अनुसार नीति को बंद कर दें।
| नियंत्रण | उद्देश्य | गलत कॉन्फ़िगरेशन पर विफलता मोड |
|---|---|---|
| hedge delay | केवल धीमी कॉल्स को डुप्लिकेट करना | बहुत कम होने पर QPS बढ़ता है |
| maxAttempts | समवर्ती प्रतियों को सीमित करना | बहुत अधिक होने पर अनुरोधों का तूफान आता है |
| cancellation | हारने वाले के संसाधनों को मुक्त करना | विफलता क्षमता का उपभोग करती रहती है |
| throttle budget | भीड़ के दौरान कड़ा करना | मेट्रिक्स गायब होने से ओवरलोड छिप जाता है |
मॉडल उत्तर
"मैं पहले पुष्टि करूँगा कि यह एक idempotent रीड है और प्रति-अनुरोध-वर्ग लेटेंसी हिस्टोग्राम बनाऊँगा। प्राइमरी भेजने के बाद, मैं केवल p95-शैली थ्रेशोल्ड, एक स्वस्थ स्वतंत्र रेप्लिका, और समवर्ती बजट की अनुमति के बाद ही एक हेज भेजूँगा। दोनों प्रयास एक समय सीमा साझा करते हैं; पहली सफलता जीतती है और प्रॉक्सी कैंसिलेशन का प्रसार करता है जबकि यह रिकॉर्ड करता है कि क्या संसाधन वास्तव में मुक्त हुए थे। अधिकतम प्रयास, टोकन थ्रॉटलिंग, कतार की गहराई और त्रुटि दर बैकएंड की रक्षा करते हैं, जबकि नियतात्मक त्रुटियों को कभी भी डुप्लिकेट नहीं किया जाता है। मैं नीति को कैनरी करूँगा और p99, फायर दर, अतिरिक्त QPS, कैंसिलेशन लेटेंसी और अनहेज्ड प्राइमरी लेटेंसी की तुलना करूँगा; एक हेज तूफान इसे स्वचालित रूप से अक्षम कर देता है।"
सामान्य गलतियाँ
हर अनुरोध को तुरंत डुप्लिकेट करना
यह हेजिंग को बिना शर्त प्रतिकृति (unconditional replication) में बदल देता है, जिससे सामान्य लोड और लागत बढ़ जाती है बिना यह साबित किए कि स्ट्रैग्लर्स ने टेल का कारण बना।
साइड-इफेक्ट वाले राइट्स को हेज करना
दो प्रयास दो रिकॉर्ड बना सकते हैं या दो बार चार्ज कर सकते हैं। Idempotency कुंजियों, डिडुप्लीकेशन और ट्रांजेक्शन सिमेंटिक्स के बिना हेज न करें।
एक ही विफलता डोमेन का उपयोग करना
साझा होस्ट, रैक, या ज़ोन विफलता दोनों प्रयासों को धीमा कर देती है और ओवरलोड स्थान पर लोड जोड़ती है।
केवल उपयोगकर्ता-दृश्यमान p99 को देखना
हेजिंग खराब होते प्राइमरी पाथ को छिपा सकती है और स्केलिंग संकेतों में देरी कर सकती है। अनहेज्ड प्राइमरी लेटेंसी और कतार की गहराई को भी रिकॉर्ड करें।
कैंसिलेशन की अनदेखी करना
प्रतीक्षा रोकना डाउनस्ट्रीम काम को रोकना नहीं है। प्रसार, संसाधन रिलीज और कैंसिलेशन लेटेंसी को सत्यापित करें।
कोई किल स्विच न होना
उच्च त्रुटियों, कतार निर्माण, या असामान्य हेज फायर दर के लिए एक तेज़ सेवा, टेनेंट, या क्षेत्र-स्तरीय डिसेबल स्विच की आवश्यकता होती है।
फॉलो-अप प्रश्न और उत्तर
हेजिंग रिट्राई (retry) से किस प्रकार भिन्न है?
रिट्राई आमतौर पर फिर से भेजने से पहले विफलता की प्रतीक्षा करता है। हेजिंग लेटेंसी थ्रेशोल्ड के बाद एक प्रति भेजता है जबकि पहला प्रयास अभी भी चल रहा होता है। दोनों को idempotency, समय सीमा और थ्रॉटलिंग की आवश्यकता होती है।
p95 से शुरुआत क्यों करें?
यह टेल के एक छोटे हिस्से को कवर करते हुए अधिकांश सामान्य अनुरोधों को अछूता छोड़ देता है। थ्रेशोल्ड को अनुरोध वर्ग, बजट और प्रयोग के परिणामों के अनुसार ट्यून किया जाना चाहिए।
क्या होगा यदि प्रत्येक रेप्लिका संकुलित (congested) हो?
हेजिंग बंद करें और दर सीमा (rate limits), कतार, गिरावट (degradation), या तेज़ विफलता का उपयोग करें। हेजिंग अपर्याप्त क्षमता की मरम्मत नहीं कर सकती है।
आप कैसे साबित करते हैं कि कैंसिलेशन काम करता है?
डाउनस्ट्रीम कैंसिलेशन, कार्य पूर्णता, कनेक्शन अधिभोग और रिलीज लेटेंसी को रिकॉर्ड करें। एक धीमे हारने वाले प्रयास को इंजेक्ट करें और पुष्टि करें कि विजेता चुने जाने के बाद यह रुक जाता है।
स्ट्रीमिंग डिज़ाइन को कैसे बदलती है?
ट्रिगर के रूप में पहले बाइट या टोकन के समय का उपयोग करें, लेकिन आउटपुट शुरू होने के बाद डुप्लिकेट करने से डुप्लिकेट डेटा बन सकता है। पहले स्ट्रीम विलय, कैंसिलेशन और क्लाइंट दृश्यता को परिभाषित करें।
प्रमुख gRPC नॉब्स (knobs) क्या हैं?
maxAttempts, hedgingDelay, और गैर-घातक स्थिति कोड नियंत्रित करते हैं कि प्रतियां कब भेजी जाती हैं। gRPC प्रयासों को 5 तक सीमित करता है और रिट्राई थ्रॉटलिंग और सर्वर पुशबैक प्रदान करता है; सेवा को अभी भी अपने स्वयं के क्षमता बजट की आवश्यकता होती है।