2009-12-30 14 views
10

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

अब तक हम स्प्रिंग लोडर मॉक निर्भरताओं के लिए स्प्रिंगरुनर का उपयोग कर रहे हैं, जो काम करता है। दो चीजें जिन्हें हम इस बारे में पसंद नहीं करते हैं 1) वसंत ढांचे को लोड किया जाना चाहिए और प्रत्येक बार उन परीक्षणों को चलाने के लिए शुरू किया जाना चाहिए जो वास्तव में तेज़ नहीं हैं, और 2) हमें वास्तविक वर्गों के रूप में सभी नकली निर्भरताओं को स्पष्ट रूप से बनाने के लिए मजबूर होना पड़ता है, जो कुछ JMockit खत्म करने में मदद करता है।

यहाँ हम क्या परीक्षण कर रहे हैं की एक सरल उदाहरण है:

public class UnitUnderTest { 

    @Autowired 
    ISomeInterface someInterface; 

    public void callInterfaceMethod() { 

     System.out.println("UnitUnderTest.callInterfaceMethod calling someInterface.doSomething"); 
     someInterface.doSomething(); 
    } 

} 

तो, सवाल है, वहाँ JMockit एक नकली someInterface बनवाने के लिए एक रास्ता है?

+0

यह भी देखें: http://stackoverflow.com/questions/1638911/mock-object-and-spring-annotations –

उत्तर

10

JMockit हमेशा (एक अंतिम नकली क्षेत्र के मामले को छोड़कर) एक मज़ाक उड़ाया इंटरफ़ेस का दृष्टांत होगा, लेकिन यह है कि केवल परीक्षण कोड में होता है। यह परीक्षण के तहत कोड में स्वचालित रूप से उदाहरण इंजेक्ट नहीं करेगा।

आपको मैन्युअल रूप से नकली उदाहरण इंजेक्ट करना होगा। उदाहरण के लिए:

public class SomeTest 
{ 
    @Autowired UnitUnderTest unitUnderTest; 
    @Mocked ISomeInterface theMock; // created and assigned automatically 

    @Test 
    public void testSomeMethod() 
    { 
     Deencapsulation.setField(unitUnderTest, theMock); 
     //proceed with unit test here 
    } 
} 

mockit.Deencapsulation एक प्रतिबिंब आधारित उपयोगिता वर्ग आप निजी विधियां प्रारंभ,/सेट क्षेत्रों प्राप्त करने देता है कि, आदि

+4

बस एक नोट: चूंकि यह उत्तर पोस्ट किया गया था, इसलिए जेमॉकिट ने परीक्षण कक्षाओं में नकली वस्तुओं के स्वचालित इंजेक्शन के लिए समर्थन जोड़ा है। इस उदाहरण में, '@ ऑटोवायर' को '@ टेस्टेड' और '@ मॉक'' के साथ' @ इंजेक्शन योग्य 'के साथ बदलें। –

+0

वाह @ Rogério! यह अच्छा है! जेमॉकिट इतना शक्तिशाली है ... मैं इसे प्यार कर रहा हूँ !! –

+0

@ Rogério jmockit कवरेज टूल mockito के लिए रिपोर्ट उत्पन्न कर सकते हैं? हमारे विरासत परीक्षण कोड mockito के साथ है। कोई लिंक उपयोगी है। – yuyue007

8

आप अपने परीक्षण मामले में अपने मॉक ISomeInterface को स्पष्ट रूप से इंजेक्ट करने के लिए org.springframework.test.util.ReflectionTestUtils का उपयोग कर सकते हैं।

देखें documentation

+1

(+1) यह एक अच्छी कक्षा है जिसे मैं नहीं जानता :) – Bozho

+0

मुझे इन्हें ढूंढना अच्छा लगता है वसंत एपीआई में छोटे रत्न ... +1 – skaffman

+0

यह सुनिश्चित करने के लिए एक उपयोगी वर्ग है। फिर भी, स्पष्ट रूप से नकली बनाने के लिए जेमॉकिट का उपयोग करने के मुख्य कारणों में से एक को हरा देता है। – SwimsZoots

4
संकेत कृपया ऊपर दी गई साथ

है, यहाँ है कि मैं क्या के रूप में सबसे अधिक उपयोगी पाया है JMockit के लिए कोई नया नया: JMockit Deencapsulation कक्षा प्रदान करता है ताकि आप निजी आश्रित क्षेत्रों (वसंत पुस्तकालयों को खींचने की कोई आवश्यकता नहीं) के मूल्य निर्धारित कर सकें, और MockUp कक्षा जो आपको स्पष्ट रूप से एक इंटरफ़ेस और नकली कार्यान्वयन करने की अनुमति देती है इंटरफेस के एक या अधिक तरीकों। यहां बताया गया है कि मैंने इस विशेष मामले को हल करने का अंत कैसे किया:

@Before 
public void setUp() { 

    IMarketMakerDal theMock = new MockUp <IMarketMakerDal>() { 

     @Mock 
     MarketMakerDcl findByMarketMakerGuid(String marketMakerGuid) { 

     MarketMakerDcl marketMakerDcl = new MarketMakerDcl(); 
     marketMakerDcl.setBaseCurrencyCode(CURRENCY_CODE_US_DOLLAR); 
     return marketMakerDcl; 
     } 
    }.getMockInstance(); 

    setField(unitUnderTest, theMock); 
} 

सहायता के लिए सभी को धन्यवाद।

2

उन लोगों को जब jmockit का उपयोग कर spring (या) ढांचे में @autowired क्षेत्र उपहास करने के लिए जो

java.lang.IllegalStateException: Missing @Injectable for field *** 

या

java.lang.IllegalStateException: Missing @Tested class for field *** 

त्रुटि से मुलाकात के लिए, मैं दो कदम ऊपर त्रुटियां से बचने के लिए नीचे किया:

  1. का उपयोग करेंबजाय @Tested

https://groups.google.com/forum/#!msg/jmockit-users/uo0S51lSX24/lQhLNN--eJcJ

के पीछे
  1. वापस लाएं JMockit के संस्करण 1.18 या पिछले अभियानों

https://groups.google.com/forum/#!topic/jmockit-users/wMFZggsA8LM

को
0

यदि आपके पास इंटरफ़ेस के लिए @ क्वालिफायर एनोटेशन है, तो आपको अपने @ इंजेक्शन योग्य फ़ील्ड को ठीक से नामित करने की आवश्यकता है क्योंकि इसे क्वालीफायर में नाम दिया गया है।

कस्टम नाम जावा ईई (@Resource (नाम), @Named) या स्प्रिंग फ्रेमवर्क (@Qualifier) ​​से क्षेत्र एनोटेशन में निर्दिष्ट किया जाता है जब एक मिलान की तलाश:

यहाँ JMockit doc से उद्धरण है @ इंजेक्शन योग्य या @ टेस्टेड मान। जब इस तरह के नाम में एक - (डैश) या। (डॉट) चरित्र, इसके विपरीत इसी ऊंट-काज्ड नाम का उपयोग किया जाता है।

उदाहरण के लिए:

@Component 
public class AClass { 

    @Autowired 
    private Bean1 bean1; 

    @Autowired 
    @Qualifier("my-dashed-name") 
    private AmqpTemplate rpcTemplate; 
} 

यूनिट परीक्षण वर्ग:

public class AClassTest { 

    @Injectable 
    private Bean1 bean1; 

    @Injectable 
    private AmqpTemplate myDashedName; 

    @Tested 
    private AClass aClass = new AClass(); 
} 

इसके अलावा प्रत्येक @Autowired सेम के लिए setFiled उपयोग करने की आवश्यकता है, सभी क्षेत्रों injects स्वचालित रूप से जब @Tested वर्ग instantiated है । JMockit ver पर परीक्षण किया। 1.30

संबंधित मुद्दे