AppSignal पर हम रूबी एप्लिकेशन के लिए एरर ट्रैकिंग प्रदान करते हैं। ऐसा करने के लिए, हम एप्लिकेशन द्वारा हम पर फेंके गए सभी एक्सेप्शन्स को कैप्चर करते हैं और डेवलपर्स को सूचित करते हैं जैसे ही वे होते हैं।
एक्सेप्शन हैंडलिंग को सही करना मुश्किल हो सकता है। इस लेख में हम बताएंगे कि यह कैसे काम करता है, खराब हैंडलिंग से क्या समस्याएं हो सकती हैं और एक्सेप्शन्स को सही तरीके से कैसे रेस्क्यू करें।
एक्सेप्शन्स रेस्क्यू करना
रूबी में एक्सेप्शन्स को रेस्क्यू करके आप अपने एप्लिकेशन को उस क्षण क्रैश होने से रोक सकते हैं जब कुछ गलत होता है। begin .. rescue ब्लॉक के साथ आप अपने एप्लिकेशन के लिए एक वैकल्पिक पथ निर्दिष्ट कर सकते हैं जब एरर होती है।
यह भी संभव है कि कौन से एक्सेप्शन्स रेस्क्यू किए जाने चाहिए। जब एक एक्सेप्शन क्लास निर्दिष्ट की जाती है, तो इस एक्सेप्शन के सभी सबक्लास भी कैप्चर किए जाएंगे।
उपरोक्त उदाहरण में आप देख सकते हैं कि एक्सेप्शन Errno::ENOENT तब पकड़ा जाता है जब इसके पैरेंट SystemCallError को रेस्क्यू किया जा रहा है।
एक्सेप्शन चेन में बहुत ऊपर रेस्क्यू करना
एक्सेप्शन चेन में बहुत ऊपर एक्सेप्शन्स को रेस्क्यू नहीं करना महत्वपूर्ण है। जब आप ऐसा करते हैं, तो सभी सबक्लास्ड एक्सेप्शन्स भी पकड़े जाएंगे, जिससे रेस्क्यू ब्लॉक का कैप्चर बहुत सामान्य हो जाता है।
यहां एक प्रोग्राम है जो प्रोग्राम को पास किए गए आर्गुमेंट के आधार पर एक कॉन्फिग फ़ाइल पढ़ता है।
एरर संदेश कहता है कि यह कॉन्फिग फ़ाइल नहीं पढ़ सका, लेकिन असली समस्या कोड में टाइपो थी।
begin .. rescue ब्लॉक द्वारा पकड़ा गया डिफ़ॉल्ट एक्सेप्शन क्लास StandardError है। यदि हम कोई विशिष्ट क्लास पास नहीं करते हैं, तो रूबी StandardError और सभी सबक्लास्ड एरर्स को रेस्क्यू करेगा। NoMethodError इन एरर्स में से एक है।
एक विशिष्ट एक्सेप्शन क्लास को रेस्क्यू करने से असंबंधित एरर्स को गलती से विफलता स्थिति को प्रेरित करने से रोकने में मदद मिलेगी। यह अधिक विशिष्ट कस्टम एरर संदेशों की भी अनुमति देता है जो अंतिम उपयोगकर्ता के लिए अधिक सहायक होते हैं।
Exception रेस्क्यू करना
एक्सेप्शन चेन में ऊपर रेस्क्यू करना अभी भी आकर्षक हो सकता है। एक एप्लिकेशन द्वारा उठाए जा सकने वाले सभी एरर्स को रेस्क्यू करने से यह क्रैश होने से बच जाएगा। (100% अपटाइम यहां हम आते हैं!) हालांकि, यह बहुत सारी समस्याएं पैदा कर सकता है।
Exception क्लास रूबी में मुख्य एक्सेप्शन क्लास है। अन्य सभी एक्सेप्शन्स इस क्लास के सबक्लास हैं; यदि Exception रेस्क्यू किया जाता है तो सभी एरर्स पकड़े जाएंगे।
दो एक्सेप्शन्स जो अधिकांश एप्लिकेशन रेस्क्यू नहीं करना चाहेंगे वे हैं SignalException और SystemExit।
SignalException का उपयोग तब किया जाता जब कोई बाहरी स्रोत एप्लिकेशन को रोकने के लिए कह रहा हो। यह ऑपरेटिंग सिस्टम हो सकता है जब वह शट डाउन करना चाहता हो, या एक सिस्टम एडमिनिस्ट्रेटर जो एप्लिकेशन को रोकना चाहता हो। उदाहरण
SystemExit का उपयोग तब किया जाता है जब रूबी एप्लिकेशन से exit कॉल किया जा रहा हो। जब यह उठाया जाता है तो डेवलपर एप्लिकेशन को रोकना चाहता है। उदाहरण
यदि हम Exception रेस्क्यू करते हैं और ये एक्सेप्शन्स उठाए जाते हैं जबकि एप्लिकेशन वर्तमान में begin ... rescue ... end ब्लॉक चला रहा है तो यह बाहर नहीं निकल सकता।
सामान्य स्थितियों में Exception रेस्क्यू करना आमतौर पर बुरा विचार है। Exception रेस्क्यू करते समय, आप SignalException और SystemExit को कार्य करने से रोकेंगे, लेकिन LoadError, SyntaxError और NoMemoryError को भी, कुछ नाम रखने के लिए। अधिक विशिष्ट एक्सेप्शन्स को रेस्क्यू करना बेहतर है।
टेस्ट्स में विफलताएं
जब Exception रेस्क्यू किया जाता है, rescue Exception => e का उपयोग करके, आपके एप्लिकेशन के अलावा अन्य चीजें टूट सकती हैं। टेस्ट सूट वास्तव में कुछ एरर्स को छिपा सकता है।
minitest और RSpec में विफल असर्शन एक्सेप्शन उठाकर असफल असर्शन के बारे में सूचित करेंगे, टेस्ट को विफल करेंगे। जब वे ऐसा करते हैं, तो वे अपने स्वयं के कस्टम एक्सेप्शन्स उठाते हैं, जो Exception से सबक्लास्ड होते हैं।
यदि Exception टेस्ट में या एप्लिकेशन कोड में रेस्क्यू किया जाता है, तो यह असर्शन विफलता को चुप करा सकता है।
एक्सेप्शन्स की अपेक्षा करना
कुछ कोड एक्सेप्शन्स उठाने के लिए होता है। टेस्ट सूट में एक्सेप्शन को केवल चुप कराना संभव है ताकि जब वे उठाए जाएं तो टेस्ट विफल न हो।
हालांकि, यह टेस्ट नहीं करता कि एक्सेप्शन उठाया गया था या नहीं। जब एक्सेप्शन नहीं उठाया जाता, तो आपका टेस्ट यह बताने में सक्षम नहीं होगा कि व्यवहार अभी भी सही है।
यह दावा करना संभव है कि एक्सेप्शन उठाया गया है, और यदि नहीं, तो कौन सा एक्सेप्शन था।
Exception को फिर से उठाएं
एक एप्लिकेशन को केवल एक्सेप्शन चेन में Exception क्लास जितना ऊपर कैप्चर करना चाहिए जब इसके लिए बहुत अच्छा कारण हो। उदाहरण के लिए, जब कोड के ब्लॉक से बाहर निकलने से पहले कुछ सफाई शामिल हो, जैसे अस्थायी फ़ाइलों को हटाना जिन्हें वास्तव में हटाने की आवश्यकता है।
जब आपको बिल्कुल Exception रेस्क्यू करना हो, तो एक सिफारिश यह है कि इसे संभालने के बाद फिर से उठाएं। इस तरह रूबी एक्सेप्शन हैंडलिंग बाद में प्रोसेस के भाग्य का फैसला कर सकती है।
अनिश्चित क्या रेस्क्यू करें?
जैसा कि पहले उल्लेख किया गया है, रेस्क्यू करने के लिए कौन सी एरर्स विशिष्ट होना अच्छा है।
जब आप अनिश्चित हों कि एक ऑपरेशन कौन से एक्सेप्शन्स उठा सकता है, तो StandardError रेस्क्यू करना एक अच्छी शुरुआत हो सकती है। अपने कोड को विभिन्न परिदृश्यों में चलाएं और देखें कि यह कौन से एक्सेप्शन्स उठाता है।
हर बार जब आप एक नए एक्सेप्शन का सामना करते हैं, तो उन एक्सेप्शन्स या उनके प्रासंगिक पैरेंट क्लास के लिए विशिष्ट रेस्क्यू केस जोड़ें। बहुत सारे एक्सेप्शन्स रेस्क्यू करने के बजाय क्या रेस्क्यू करना है इसमें विशिष्ट होना बेहतर है।
यह रूबी में एक्सेप्शन हैंडलिंग पर हमारे प्राइमर का समापन करता है। यदि आप अधिक जानना चाहते हैं, या कोई विशिष्ट प्रश्न है तो @AppSignal पर हमें बताएं। यदि आप अपने ऐप में एक्सेप्शन्स कहां और कितनी बार उठाए जाते हैं, इसकी बेहतर अंतर्दृष्टि चाहते हैं, तो AppSignal आज़माएं।
