2012-01-16 10 views
30

में अपेक्षित पैरामीटर मानों की पुष्टि करने के लिए सत्यापन का उपयोग करना मैं यह सत्यापित करने की कोशिश कर रहा हूं कि किसी मॉक के भीतर एक विधि अपेक्षित ऑब्जेक्ट पैरामीटर के साथ कॉल की जाती है। मैं Moq, nUnit का उपयोग कर रहा हूं, और सोच रहा हूं कि ऑटोफिक्चर की लचीलापन को नौकरी मिलनी चाहिए। नीचे जो मैं करने की कोशिश कर रहा हूं उसका सरलीकृत संस्करण नीचे है।Moq mock class

क्या ऑटोफिक्चर के साथ ऐसा करने का कोई तरीका है? क्या सत्यापित करने के लिए कोई बेहतर तरीका है कि Something उचित पैरामीटर के साथ बुलाया जाता है?

अधिभावी A कक्षा में बराबर संपत्ति मूल्यों की तुलना और Verify लाइन को बदलने के लिए:

barMock.Verify(m => m.Something(a)); 

गुजरता है, तथापि मैं नहीं बल्कि हावी नहीं होता अपने प्रोजेक्ट में एक की तरह हर कक्षा में बराबर होती है।

namespace Test 
{ 
    using Moq; 
    using NUnit.Framework; 
    using Ploeh.SemanticComparison.Fluent; 

    public class A 
    { 
     public int P1 { get; set; } 
    } 
    public interface IBar 
    { 
     void Something(A a); 
    } 

    public class Foo 
    { 
     public A Data { get; private set; } 
     public void DoSomethingWith(IBar bar) 
     { 
      Data = new A { P1 = 1 }; 
      bar.Something(Data); 
     } 
    } 

    [TestFixture] 
    public class AutoFixtureTest 
    { 
     [Test] 
     public void TestSample() 
     { 
      var foo = new Foo(); 
      var barMock = new Mock<IBar>(); 
      var a = new A { P1 = 1 }; 
      var expectedA = a.AsSource().OfLikeness<A>(); 

      foo.DoSomethingWith(barMock.Object); 

      expectedA.ShouldEqual(foo.Data); // passes 
      barMock.Verify(m => m.Something(expectedA.Value)); // fails 
     } 
    } 
} 

उत्तर

45

Verify में MOQ डिफ़ॉल्ट चेक द्वारा बहस के लिए समानता का संदर्भ तो यह केवल गुजरता है जब आप एक ही उदाहरण हैं प्रदान करते हैं (सिवाय आप Equals ओवरराइड किया हुआ है) अपने परीक्षण में और अपने कार्यान्वयन में।

आपके मामले में expectedA.Value केवल new A { P1 = 1 } परीक्षण में बनाया गया है जो निश्चित रूप से DoSomethingWith में बनाया गया एक ही उदाहरण नहीं है।

आप Equals अधिभावी बिना Moq के It.Is निर्माण का उपयोग करने के लिए ठीक से इस परीक्षण करने के लिए (इस के लिए वास्तव में आप बिल्कुल Autofixture जरूरत नहीं है) की जरूरत है:

barMock.Verify(m => m.Something(It.Is<A>(arg => arg.P1 == a.P1))); 

लेकिन अगर आप P1 जैसे कई गुण होते हैं, P2 , पी 3 ... AutoFixture उपयोगी हो सकता है:

barMock.Verify(m => m.Something(It.Is<A>(arg => expectedA.Equals(a)))); 

क्योंकि आप सभी गुण के लिए मैन्युअल रूप से eqaulity चेक लिखने के लिए जरूरत नहीं है।

+2

+1 विशेष रूप से आखिरी समाधान लिकनेस के साथ सही दृष्टिकोण है। FWIW Likeness के लिए एक नई कार्यक्षमता के लिए एक कार्य आइटम है जो इसे एक प्रॉक्सी को गतिशील रूप से निकालने में सक्षम बनाता है जो समानता को ओवरराइड करता है, जो उपर्युक्त वाक्यविन्यास को बहुत सरल बनाता है: http://autofixture.codeplex.com/workitem/4230 –

+0

ऐसा हुआ, धन्यवाद ! – jaminto

5

यदि आप ऑटोफिक्चर 2.9.1 (या नए) में अपग्रेड करते हैं तो आप लिक्विनेस इंस्टेंस पर CreateProxy विधि को कॉल कर सकते हैं जो गंतव्य प्रकार के लिए गतिशील प्रॉक्सी उत्सर्जित करेगा।

जेनरेटेड गतिशील प्रॉक्सी ओवरक्साइड समानता का उपयोग करके बराबर है जो सिंटैक्स को सरल बनाता है (काफी कुछ)।

[Test] 
public void TestSample() 
{ 
    var foo = new Foo(); 
    var barMock = new Mock<IBar>(); 
    var expected = new A().AsSource().OfLikeness<A>().CreateProxy(); 
    expected.P1 = 1; 

    foo.DoSomethingWith(barMock.Object); 

    Assert.True(expected.Equals(foo.Data));  // passes 
    barMock.Verify(m => m.Something(expected)); // passes 
} 

ध्यान दें कि यह भी परीक्षण अभिकथन ज्यादा किसी भी उदाहरण को स्वीकार करने की तुलना में अधिक विशिष्ट बनाता है:

यहाँ मूल परीक्षण विधि, छवि प्रॉक्सी का उपयोग करने के लिए संशोधित है।

आप इस नई सुविधा here पर अधिक जानकारी प्राप्त कर सकते हैं।