unit testing यूनिट परीक्षण के लिए नया, महान परीक्षण कैसे लिखें?




यूनिट टेस्ट क्या है (7)

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

When I'm writing tests for a method, I have the feeling of rewriting a second time what I          
already wrote in the method itself.
My tests just seems so tightly bound to the method (testing all codepath, expecting some    
inner methods to be called a number of times, with certain arguments), that it seems that
if I ever refactor the method, the tests will fail even if the final behavior of the   
method did not change.

ऐसा इसलिए है क्योंकि आप अपना कोड लिखने के बाद अपने परीक्षण लिख रहे हैं। यदि आपने इसे दूसरी तरफ किया (पहले परीक्षणों को लिखा) तो यह इस तरह से महसूस नहीं करेगा।

मैं इकाई परीक्षण दुनिया के लिए बिल्कुल नया हूं, और मैंने अभी इस सप्ताह अपने मौजूदा ऐप के लिए परीक्षण कवरेज जोड़ने का फैसला किया है।

यह एक बड़ा काम है, ज्यादातर परीक्षण करने के लिए कक्षाओं की संख्या के कारण, बल्कि इसलिए कि लेखन परीक्षण मेरे लिए बिल्कुल नया है।

मैंने पहले ही कक्षाओं के समूह के लिए परीक्षण लिखे हैं, लेकिन अब मैं सोच रहा हूं कि मैं इसे सही कर रहा हूं।

जब मैं किसी विधि के लिए परीक्षण लिख रहा हूं, तो मुझे दूसरी बार फिर से लिखने की भावना है जो मैंने पहले ही विधि में लिखा है।
मेरे परीक्षण बस विधि से इतने कड़े बाध्य लगते हैं (सभी कोडपैथ का परीक्षण, कुछ आंतरिक तरीकों को कुछ तर्कों के साथ कई बार बुलाया जाने की उम्मीद है), ऐसा लगता है कि अगर मैंने कभी विधि को दोबारा प्रतिक्रिया दी है, तो परीक्षण विफल हो जाएंगे विधि का अंतिम व्यवहार नहीं बदला।

यह सिर्फ एक भावना है, और जैसा कि पहले कहा गया था, मुझे परीक्षण का कोई अनुभव नहीं है। अगर वहां कुछ और अनुभवी परीक्षकों ने मुझे सलाह दी है कि मौजूदा ऐप के लिए महान परीक्षण कैसे लिखें, तो इसकी सराहना की जाएगी।

संपादित करें: मुझे स्टैक ओवरफ़्लो का शुक्रिया अदा करना अच्छा लगेगा, मेरे पास बहुत कम इनपुट था कि 15 मिनट जो मैंने ऑनलाइन पढ़ने के अधिक घंटों का उत्तर दिया था।


जिस विधि को परीक्षण करने जा रहा है उसे लिखने से पहले यूनिट टेस्ट लिखने का प्रयास करें।

यह निश्चित रूप से आपको कुछ अलग तरीके से सोचने के लिए मजबूर करेगा कि चीजें कैसे की जा रही हैं। आपको पता नहीं चलेगा कि विधि कैसे काम करने जा रही है, बस इसे क्या करना है।

आपको हमेशा विधि के परिणामों का परीक्षण करना चाहिए, न कि विधि को उन परिणामों को कैसे प्राप्त किया जाता है।


यूनिट परीक्षण के लिए, मुझे टेस्ट ड्राइव (दोनों परीक्षण, कोड दूसरा) और कोड पहले पाया गया, परीक्षण करने के लिए दूसरा परीक्षण बेहद उपयोगी है।

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

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

function square(number) जैसे सभी सरल उदाहरण बहुत अच्छे हैं और सभी संभवतः खराब उम्मीदवारों को बहुत समय व्यतीत करने के लिए खर्च करते हैं। वे जो महत्वपूर्ण व्यावसायिक तर्क करते हैं, जहां परीक्षण महत्वपूर्ण है। आवश्यकताओं का परीक्षण करें। नलसाजी का परीक्षण न करें। यदि आवश्यकताएं बदलती हैं तो अनुमान लगाएं कि परीक्षण भी होना चाहिए।

परीक्षण का सचमुच परीक्षण नहीं किया जाना चाहिए कि फ़ंक्शन फू ने फंक्शन बार को 3 बार बुलाया। यह गलत है। जांचें कि क्या परिणाम और दुष्प्रभाव सही हैं, न कि आंतरिक यांत्रिकी।


अपने कोड का पूर्ण कवरेज प्राप्त करने के लिए परीक्षण न लिखें। परीक्षणों को लिखें जो आपकी आवश्यकताओं की गारंटी देते हैं। आप कोडपैथ खोज सकते हैं जो अनावश्यक हैं। इसके विपरीत, यदि वे आवश्यक हैं, तो वे किसी प्रकार की आवश्यकता को पूरा करने के लिए हैं; यह पता लगाएं कि यह क्या है और आवश्यकता का परीक्षण करें (पथ नहीं)।

अपने परीक्षणों को छोटा रखें: प्रति आवश्यकता एक परीक्षण।

बाद में, जब आपको कोई बदलाव करने की आवश्यकता होती है (या नया कोड लिखें), पहले एक टेस्ट लिखने का प्रयास करें। बस एक ठो। फिर आप परीक्षण संचालित विकास में पहला कदम उठाएंगे।


मेरे परीक्षण बस विधि से इतने कड़े बाध्य लगते हैं (सभी कोडपैथ का परीक्षण, कुछ आंतरिक तरीकों को कुछ तर्कों के साथ कई बार बुलाया जाने की उम्मीद है), ऐसा लगता है कि अगर मैंने कभी विधि को दोबारा प्रतिक्रिया दी है, तो परीक्षण विफल हो जाएंगे विधि का अंतिम व्यवहार नहीं बदला।

मुझे लगता है कि आप इसे गलत कर रहे हैं।

एक इकाई परीक्षण चाहिए:

  • एक विधि का परीक्षण करें
  • उस विधि के लिए कुछ विशिष्ट तर्क प्रदान करें
  • परीक्षण करें कि परिणाम अपेक्षित है

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

यदि आपकी विधि अन्य कक्षाओं में सार्वजनिक विधियों को कॉल करती है, और इन कॉलों को आपके इंटरफ़ेस द्वारा गारंटी दी जाती है, तो आप परीक्षण कर सकते हैं कि इन कॉलों को एक मॉकिंग फ्रेमवर्क का उपयोग करके किया जा रहा है।

अपेक्षित परिणाम गतिशील रूप से उत्पन्न करने के लिए आपको विधि (या इसका उपयोग करने वाला आंतरिक कोड) का उपयोग नहीं करना चाहिए। अपेक्षित परिणाम आपके परीक्षण मामले में कड़ी-कोडित होना चाहिए ताकि कार्यान्वयन में परिवर्तन होने पर यह परिवर्तित न हो। एक यूनिट परीक्षण क्या करना चाहिए इसका एक सरल उदाहरण यहां दिया गया है:

testAdd()
{
    int x = 5;
    int y = -2;
    int expectedResult = 3;

    Calculator calculator = new Calculator();
    int actualResult = calculator.Add(x, y);
    Assert.AreEqual(expectedResult, actualResult);
}

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


यह ध्यान देने योग्य है कि मौजूदा कोड में रेट्रो-फिटिंग यूनिट परीक्षण पहले कोड में परीक्षण के साथ उस कोड के निर्माण को चलाने से कहीं अधिक कठिन है। यह विरासत अनुप्रयोगों से निपटने में बड़े प्रश्नों में से एक है ... इकाई परीक्षण कैसे करें? यह कई बार पहले पूछा गया है (इसलिए आपको एक डुप्लिकेट प्रश्न के रूप में बंद किया जा सकता है), और लोग आमतौर पर यहां समाप्त होते हैं:

मौजूदा कोड को टेस्ट संचालित विकास में स्थानांतरित करना

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


इकाई परीक्षण के लिए यह सबसे अच्छी किताब है: manning.com/osherove

यह सभी सर्वोत्तम प्रथाओं को बताता है, करता है, और यूनिट परीक्षण के लिए नहीं है।







testing