2012-05-16 11 views
33

मैं इंटरनेट से पढ़ा है मैं इस अंक जो इंटरफेस इसरिपोजिटरी पैटर्न - हमें इंटरफेस की ज़रूरत क्यों है?

  • उपयोग TDD तरीकों
  • दृढ़ता इंजन

बदलें के लिए प्रयोग किया जाता है का कहना है कि मिल गया लेकिन मैं समझने के लिए इंटरफेस होगा नहीं पा रहा हूँ Replace persistance engine इस बिंदु पर उपयोगी हो। पर विचार मैं EmployeeRepository

public class EmployeeRepository 
{ 
    public employee[] GetAll() 
    { 
    //here I'll return from dbContext or ObjectContex class 
    } 
} 

के लिए एक बुनियादी (जेनरिक के बिना) भंडार बना रहा हूं तो कैसे इंटरफेस चित्र में आने की सुविधा देता है?

और यदि मान लीजिए कि मैंने एक इंटरफ़ेस बनाया है तो क्यों उतार चढ़ाव का उपयोग किया जाता है? उदाहरण के लिए

IEmployee emp = new EmployeeRepository() ; 
vs 
EmployeeRepository emp = new EmployeeRepository(); 

कृपया मुझे रिपोजिटरी पैटर्न के संबंध में इंटरफेस की सटीक और अन्य उपयोगीता समझाएं।

उत्तर

69

तो इंटरफ़ेस तस्वीर में कैसे आते हैं?

इस तरह

:

public interface IEmployeeRepository 
{ 
    Employee[] GetAll(); 
} 

और फिर आप के रूप में कई कार्यान्वयन के रूप में आप की तरह हो सकता है:

public class EmployeeRepositoryEF: IEmployeeRepository 
{ 
    public Employee[] GetAll() 
    { 
     //here you will return employees after querying your EF DbContext 
    } 
} 

public class EmployeeRepositoryXML: IEmployeeRepository 
{ 
    public Employee[] GetAll() 
    { 
     //here you will return employees after querying an XML file 
    } 
} 

public class EmployeeRepositoryWCF: IEmployeeRepository 
{ 
    public Employee[] GetAll() 
    { 
     //here you will return employees after querying some remote WCF service 
    } 
} 

and so on ... you could have as many implementation as you like 

आप यह वास्तव में महत्वपूर्ण नहीं है कि हम कैसे भंडार को लागू देख सकते हैं।महत्वपूर्ण बात यह है कि सभी भंडार और कार्यान्वयन परिभाषित अनुबंध (इंटरफ़ेस) का सम्मान करते हैं और सभी में GetAll कर्मचारियों की सूची लौटने की विधि होती है।

और फिर आपके पास एक नियंत्रक होगा जो इस इंटरफ़ेस का उपयोग करता है।

public class EmployeesController: Controller 
{ 
    private readonly IEmployeeRepository _repository; 
    public EmployeesController(IEmployeeRepository repository) 
    { 
     _repository = repository; 
    } 

    public ActionResult Index() 
    { 
     var employees = _repository.GetAll(); 
     return View(employees); 
    } 
} 

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

  1. स्थापित Ninject.MVC3 NuGet
  2. उत्पन्न ~/App_Start/NinjectWebCommon.cs कोड आप बस कोड की एक लाइन के साथ एफई कार्यान्वयन उपयोग करने का निर्णय में:

    यह इस तरह Ninject साथ किया जाता है, इसका एक उदाहरण

    private static void RegisterServices(IKernel kernel) 
    { 
        kernel.Bind<IEmployeeRepository>().To<EmployeeRepositoryEF>(); 
    }   
    

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

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

मैं आपको एएसपी.नेट एमवीसी में टीडीडी और डी के बारे में following articles चेकआउट करने के लिए भी आमंत्रित करता हूं।

+1

अद्भुत उत्तर, प्रत्येक स्पष्टीकरण योग्य है .. अब मुझे यह पता चलता है कि चीजें कैसे काम करती हैं .. धन्यवाद, मैं इस उत्तर को स्वीकार नहीं कर सकता क्योंकि मेरे अंक 15 से नीचे हैं, जैसे ही मैं कमाता हूं, मैं इसे उत्तर के रूप में स्वीकार करूंगा। – Meson

+0

उस लेख के लिए धन्यवाद .. और मान लीजिए कि अगर मैं अपने निर्भरता इंजेक्शन ढांचे में 'कर्मचारी रिपोजिटरीईएफ' को कॉन्फ़िगर करता हूं, तो मेरा नियंत्रक इस 'कर्मचारी रिपोजिटरीएफ़' का उपभोग करेगा, लेकिन अगर मैं उसी नियंत्रक में 2 कार्यान्वयन का उपभोग करना चाहता हूं .. यदि यह प्रश्न बेवकूफ im बहुत खेद है .. – Meson

+2

उदाहरण में मैं प्रदाता नियंत्रक को अपने कंस्ट्रक्टर में 'आईएमएमबीआई रिपोजिटरी' उदाहरण की अपेक्षा करता है। केवल एक ही कार्यान्वयन पारित किया जा सकता है। दूसरी ओर आप एक और नियंत्रक हो सकता है जिसे इंटरफ़ेस के एक अलग कार्यान्वयन की आवश्यकता हो सकती है। यह पूरी तरह से संभव है। आपको बस अपने डी ढांचे को कॉन्फ़िगर करने की आवश्यकता है ताकि यह नियंत्रक ए में कार्यान्वयन ए और नियंत्रक बी में कार्यान्वयन बी को इंजेक्ट करे। सिंटैक्स निश्चित रूप से विभिन्न डी ढांचे के बीच भिन्न होगा। –

14

आप एक इंटरफेस के रूप में अपने भंडार का पर्दाफाश होगा:

public class EmployeeRepository : IEmployeeRepository 
{ 
    public List<Employee> GetAll() 
    { 
     // Return from db. 
    } 
} 

या एक:

public interface IEmployeeRepository 
{ 
    List<Employee> GetAll(); 
} 

यह आप इस तरह डिफ़ॉल्ट के रूप में कई अलग अलग कार्यान्वयन इंटरफेस, के है करने की अनुमति होगी परीक्षण एक:

public class TestEmployeeRepository : IEmployeeRepository 
{ 
    public List<Employee> GetAll() 
    { 
     // Stub some dummy data. 
    } 
} 

आपका कोड उपभोक्ता भंडार उसके बाद ही इंटरफ़ेस का उपयोग कर में रुचि रखता है:

IEmployeeRepository myRepo = MyRepositoryFactory.Get<IEmployeeRepository>(); 

गुप्त सॉस कारखाने, या एक प्रयोग करने योग्य प्रकार में इंटरफ़ेस को हल करने है जिसके द्वारा एक और तंत्र है (जैसे Ninject, या महल के रूप में एक निर्भरता इंजेक्शन ढांचे विंडसर इस भूमिका को पूरा करेगा)।

बिंदु है, लेने वाली कोड कार्यान्वयन, केवल अनुबंध (इंटरफेस) के बारे में परवाह नहीं है। यह आपको परीक्षण उद्देश्यों के लिए कार्यान्वयन को बहुत आसानी से स्वैप करने की अनुमति देता है और ढीले युग्मन को बढ़ावा देता है।

बस स्पष्ट करने के लिए, अंतरफलक और भंडार पैटर्न के उपयोग के बीच कोई लिंक नहीं है, यह केवल एक और पैटर्न है जो उनका उपयोग कर सकता है।

+0

आपके लिए त्वरित प्रतिक्रिया के लिए धन्यवाद ... और एक और क्यू क्यों 'Imployee emp = new EmployeeRepository(); 'बनाम' कर्मचारी रिपोजिटरी emp = new कर्मचारी रिपोजिटरी();' ?? – Meson

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