2011-05-19 10 views
13

निनजेक्ट के साथ, आप कर्नेल को कैसे कॉन्फ़िगर करते हैं ताकि मैं परिभाषित कर सकूं कि किसी ऑब्जेक्ट के त्वरण में कौन से निर्माता मूल्य गुजर रहे हैं?कंस्ट्रक्टर मूल्यों में गुजरने वाले निन

मैं है एक मॉड्यूल में विन्यस्त निम्नलिखित:

Bind<IService1>() 
    .To<Service1Impl>() 
    .InSingletonScope() 
    .Named("LIVE"); 
Bind<IService2>() 
    .To<Service2Impl>() 
    .InSingletonScope() 
    .Named("LIVE") 
    .WithConstructorArgument(
     "service1", 
     Kernel.Get<IService1>("LIVE")); 

Service2Impl IService1 के एक निर्माता पैरामीटर लेता है, लेकिन मैं इस कंटेनर से आना चाहते हैं। मैं बाइंडिंग नाम भी देना चाहता हूं क्योंकि मेरा कोड रनटाइम पर विभिन्न संस्करणों को लक्षित करेगा।

ऐसा लगता है लेकिन यह हासिल करने का सही तरीका है जो मैं करना चाहता हूं? क्या मुझे नामित बाइंडिंग के उपयोग के बिना प्राप्त करना चाहिए और कर्नेल में विभिन्न कॉन्फ़िगरेशन मॉड्यूल तारों को तारित करना चाहिए?

संपादित

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

धन्यवाद

उत्तर

12

मैं अंत में ToMethod इस्तेमाल किया है, जो मुझे आदेश समय त्रुटियों संकलन बनाए रखने के लिए निर्माताओं के साथ आवश्यक उदाहरण के निर्माण के लिए अनुमति दी।

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

.ToMethod(Func<IContext, T> method) 

Bind<IWeapon>().ToMethod(context => new Sword()); 
+1

इस वाक्यविन्यास को बहुत पसंद करते हैं। विथकॉन्स्ट्रक्टर आर्ग्यूमेंट, कंपाइलर त्रुटियों को दोबारा पकड़ता है। +1 – gb2d

+1

क्या आपके पास एक हथियार इंटरफ़ेस और तलवार ऑब्जेक्ट के लिए गंभीर रूप से एक एप्लिकेशन कॉलिंग है? – starmandeluxe

0

शायद प्रदाता आपकी मदद कर सकते हैं। एक प्रदाता के लिए बाइंड IService2। और प्रदाता के निर्माण विधि में, Service2Impl उदाहरण बनाने के लिए कर्नेल.गेट ("लाइव") का उपयोग करें।

कैसे प्रदाता https://github.com/ninject/ninject/wiki/Providers%2C-Factory-Methods-and-the-Activation-Context

+0

धन्यवाद, मुझे लगता है कि देखा। सोचा था कि यह थोड़ा अधिक कोड था और जैसा कि यह आपके द्वारा साझा किए गए लिंक में ToMethod को प्रदाता का एक दुबला संस्करण है। –

16

उपयोग करने के लिए पता करने के लिए नीचे दिए गए लिंक को देखने मैं WithConstructorParameter अधिभार कि इतने तरह एक लैम्ब्डा लेता है की सिफारिश करेंगे:

Bind<IService2>() 
    .To<Service2Impl>() 
    .InSingletonScope() 
    .Named("LIVE") 
    .WithConstructorArgument(
     "service1", 
     ctx => ctx.Kernel.Get<IService1>("LIVE")); 

यह सुनिश्चित होगा कि कि IServive1 का संकल्प होता है Service2Impl के सक्रियण के समय और कंटेनर बनने पर स्टार्टअप पर नहीं। आपके मामले में जबकि यह वास्तव में के रूप में Service1Impl सिंगलटन है कोई फर्क नहीं पड़ता, वहाँ आप मूल रूप से यह लिखा तरीके से कर रही पर दुष्प्रभाव हो सकता है:

  • निर्भरता कि WithConstructorArgument से इंजेक्ट किया जाता है के लिए बाध्यकारी पहले से ही करना पड़ता है मौजूद। इसका तात्पर्य है कि सभी बाइंडिंग को किसी विशेष क्रम में करना होता है। जब कई मॉड्यूल शामिल होते हैं तो यह रचना मुश्किल हो सकती है।

  • कस्टम स्कोप का उपयोग होने पर स्कॉइंग समस्याएं उत्पन्न हो सकती हैं। निनजा 2.0 ने कैश पेश किया और स्कोप प्रबंधन इकट्ठा किया, स्थिरता के लिए बाध्यकारी यह है कि इसे अव्यवस्था में फेंकने की संभावना है।

5

ऐसा लगता है कि आप इसे गलत तरीके से देख रहे हैं। Ninject सेवा 1 में स्वचालित रूप से सेवा 2 इंजेक्ट करेगा यदि यह इसे कन्स्ट्रक्टर तर्क के रूप में है। इस मामले में WithConstructorArgument की आवश्यकता नहीं है।

कई हैं, तो IService1 आप स्थितियों के लिए जाना चाहिए। जैसे WhenParentNamed (...)

0

मुझे लगता है कि ToConstant() क्लीनर है, InSingletonScope निहित है:

Bind<IService2>().ToConstant(new Service2Impl(argument))) 
       .Named("LIVE"); 
संबंधित मुद्दे