VS2017 .Net मानक पुस्तकालय में आंतरिक परीक्षण करने वाली इकाई


150

मैं वर्तमान में .Net Standard 1.6 पुस्तकालय बनाकर नवीनतम विज़ुअल स्टूडियो 2017 रिलीज़ कैंडिडेट के साथ खेल रहा हूँ। मैं अपने कोड का परीक्षण करने के लिए xUnit का उपयोग कर रहा हूं और सोच रहा था कि क्या आप अभी भी VS2017 में आंतरिक तरीकों का परीक्षण कर सकते हैं।

मुझे याद है कि आप VS2015 में सभी असेम्बली असेंबलीइन्फो.क्स. क्लास लगा सकते हैं, जो निर्दिष्ट परियोजनाओं को आंतरिक तरीकों को देखने में सक्षम बनाएगा

[assembly:InternalsVisibleTo("MyTests")]

जैसा कि VS2017 .Net मानक परियोजनाओं में कोई असेंबलीइन्फो.केसी क्लास नहीं है। मैं सोच रहा था कि क्या आप अभी भी आंतरिक विधियों का परीक्षण कर सकते हैं?


3
आपको बाह्य रूप से दृश्यमान कार्यक्षमता से अपने कोड का परीक्षण करने में सक्षम होना चाहिए । आखिरकार, अगर बाहरी कोड से कोई तार्किक रास्ता उन आंतरिक तरीकों तक नहीं पहुंच सकता है, तो वे पहले स्थान पर क्या कर रहे होंगे?
डेविड

3
@ डेविड मैं यह कर सकता हूं और कर सकता हूं लेकिन मैंने पहले कुछ आंतरिक कक्षाओं के आसपास सरल इकाई परीक्षण किए हैं। परीक्षण में बस अधिक स्पष्ट होना चाहिए।
फिल मरे

5
AFAIK, आप इस विशेषता को namespaceब्लॉक के बाहर किसी अन्य फ़ाइल में रख सकते हैं , और इसे संकलित करना चाहिए। इसके बारे में कुछ भी जादुई नहीं होना चाहिए AssemblyInfo.cs। यह काम नहीं करता है? बेशक, आपको सही usingक्लॉज जोड़ने या पूरी तरह से योग्य विशेषता का उपयोग करने की आवश्यकता है [assembly: System.Runtime.CompilerServices.InternalsVisibleTo("Something")]
ग्रू

1
@ डेविड यदि आप आंतरिक कक्षाओं के साथ एक पुस्तकालय बना रहे हैं और आपको इन कक्षाओं का परीक्षण और मॉक करने की आवश्यकता है, तो InternalsVisibleToयह महत्वपूर्ण है - जैसे यहाँ - stackoverflow.com/a/17574183/43453
पांडावेप

जवाबों:


210

के लिए .NET डॉक्स के अनुसारInternalsVisibleToAttribute :

विशेषता को विधानसभा स्तर पर लागू किया जाता है। इसका मतलब यह है कि इसे स्रोत कोड फ़ाइल की शुरुआत में शामिल किया जा सकता है, या इसे Visual Studio प्रोजेक्ट में असेंबलीइन्फो फ़ाइल में शामिल किया जा सकता है।

दूसरे शब्दों में, आप इसे अपने मनमाने ढंग से नामित .cs फ़ाइल में रख सकते हैं, और इसे ठीक काम करना चाहिए:

// some .cs file included in your project
using System.Runtime.CompilerServices;
[assembly:InternalsVisibleTo("MyTests")]

1
@PhilMurray: भी, ऐसा लगता है कि एक सेटिंग है जो आपको यहांAssemblyInfo.cs बताई गई "क्लासिक" फ़ाइल बनाने की अनुमति देनी चाहिए । अन्यथा सभी विशेषताओं जैसे "विवरण", "कॉपीराइट" और अन्य सामान .csproj फ़ाइल के अंदर संग्रहीत हो जाते हैं।
ग्रू

43

जैसा यहाँ वर्णित है:

https://blog.sanderaernouts.com/make-internals-visible-with-new-csproj-format

किसी अन्य ItemGroup को जोड़कर प्रोजेक्ट फ़ाइल के भीतर आंतरिक दृश्यमान विशेषता को जोड़ना संभव है:

<ItemGroup>
    <AssemblyAttribute Include="System.Runtime.CompilerServices.InternalsVisibleTo">
        <_Parameter1>$(AssemblyName).Tests</_Parameter1>
    </AssemblyAttribute>
</ItemGroup>

या और भी:

<ItemGroup>
    <AssemblyAttribute Include="System.Runtime.CompilerServices.InternalsVisibleTo">
        <_Parameter1>$(MSBuildProjectName).Tests</_Parameter1>
    </AssemblyAttribute>
</ItemGroup>

मुझे वह समाधान पसंद है क्योंकि इस तरह की चिंताओं को परिभाषित करने के लिए प्रोजेक्ट फ़ाइल सही जगह है।


8

जबकि पहला उत्तर बिल्कुल ठीक है। यदि आपको लगता है कि आप अभी भी मूल में ऐसा करना चाहते हैं, तो AssemblyInfoआप हमेशा फ़ाइल उत्पन्न नहीं करने और इसे मैन्युअल रूप से जोड़ने का विकल्प चुन सकते हैं।

<PropertyGroup>
   <GenerateAssemblyInfo>false</GenerateAssemblyInfo>
</PropertyGroup>

अधिक जानकारी के लिए: https://stackoverflow.com/a/47075759/869033


5

"इंटरनैशनलविजेंटो" विशेषता किसी भी प्रकार की "व्हाइट-बॉक्स" (दशक की अवधि, मुझे लगता है) के लिए परीक्षण है। नेट के लिए महत्वपूर्ण है। इसे मोर्चे पर "असेंबली" विशेषता के साथ किसी भी सी # फ़ाइल में रखा जा सकता है। ध्यान दें कि MS DOC का कहना है कि विधानसभा का नाम सार्वजनिक कुंजी टोकन द्वारा योग्य होना चाहिए, अगर यह हस्ताक्षरित है। कभी-कभी यह काम नहीं करता है और किसी को इसमें पूरी सार्वजनिक कुंजी का उपयोग करना चाहिए। आंतरिक तक पहुंच समवर्ती प्रणालियों के परीक्षण और कई अन्य स्थितियों में महत्वपूर्ण है। Https://www.amazon.com/xUnit-Test-Patterns-Refactoring-Code/dp/0131495054 देखें । इस पुस्तक में, मेस्ज़्रोस विभिन्न प्रकार की कोडिंग शैलियों का वर्णन करता है जो मूल रूप से कार्यक्रम के विकास के लिए "डिज़ाइन फॉर टेस्ट" दृष्टिकोण का गठन करते हैं। कम से कम यह तरीका है कि मैंने इसे वर्षों में उपयोग किया है।

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


1

दूसरा तरीका यह है कि टारगेट प्रोजेक्ट के अंदर 'रैपर' TestMyFoo पब्लिक क्लास का उपयोग करें, जिसमें आपके द्वारा परीक्षण किए जाने वाले वर्ग (जैसे MyFoo) से सार्वजनिक तरीके और विरासत हैं। ये सार्वजनिक विधियां बस उस आधार वर्ग पर कॉल करती हैं जिसे आप परीक्षण करना चाहते हैं।

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

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.