2013-01-20 58 views
8

मैंने अपनी परियोजना के लिए ServiceStack OrmLite चुना है जो एक शुद्ध डेटा-ओरिएंटेड एप्लिकेशन है। मैं अंतिम उपयोगकर्ता को अपने एक्सएमएल प्रारूप में परिभाषित अपने ऑब्जेक्ट प्रकार बनाने की अनुमति देने के लिए तैयार हूं जिसका प्रयोग CodeDOM का उपयोग कर रनटाइम पर कक्षाएं उत्पन्न करने के लिए किया जाएगा।रनटाइम पर POCO क्लास में संपत्ति जोड़ें

मैं भी आवेदन के लिए आवश्यक कुछ "प्रणाली" वस्तुओं (यानी User), लेकिन मैं सभी गुण अंत उपयोगकर्ता का उपयोग करेगा पूर्वानुमान नहीं कर सकता और इसलिए मैं एक तरह से कक्षाओं मैं में बनाने का विस्तार अनुमति देने के लिए देख रहा हूँ को परिभाषित किया जाएगा डिजाइन समय bellow उपयोगकर्ता

public class User 
{ 
    public Guid Uid { get; set; } 
    public String Username { get; set; } 
    public String Password { get; set; } 
} 

अंत नमूना एक Email और एक Address है चाहता है। उन्होंने कहा कि, (जो अभी भी OrmLite द्वारा इस्तेमाल किया जा सकता हो जाएगा उच्च वर्ग और पूरी कक्षा को 2 गुण जोड़ने के लिए सक्षम होना चाहिए, क्योंकि यह अधिलेखित करने की अनुमति देता है:

public class User 
{ 
    public Guid Uid { get; set; } 
    public String Username { get; set; } 
    public String Password { get; set; } 
    public String Email{ get; set; } 
    public String Address { get; set; } 
} 

मुझे पता करने का एक खतरा नहीं हो सकता है कि इसलिए सिस्टम को दुर्घटनाग्रस्त करने के लिए (यदि कक्षा पहले से ही तत्काल हो चुकी है) तो मैं इस मुद्दे से बचने और मेरी ज़रूरत की नकल करने का सबसे अच्छा तरीका ढूंढ रहा हूं।

उत्तर

4

ऐसा लगता है कि आप यहां क्या कर रहे हैं इसके दो भाग हैं। अतिरिक्त गुणों का समर्थन करने के लिए आपको गतिशील रूप से प्रकार बनाने की आवश्यकता है। आपको यह सुनिश्चित करने की भी आवश्यकता है कि आप कभी भी अपने ऐपडोमेन में डुप्लिकेट प्रकारों के साथ समाप्त न हों, यानी User की दो अलग-अलग परिभाषाएं।

रनटाइम प्रकार पीढ़ी

विभिन्न सुझावों को पहले से ही संभाल दिया कैसे प्रकार बनाने के लिए। एक परियोजना में, हमारे पास कुछ समान था। हमने एक बेस क्लास बनाया जिसमें मूल गुण और 'एक्सटेंशन' गुणों को संग्रहीत करने के लिए एक शब्दकोश था। फिर हमने वांछित गुणों वाले व्युत्पन्न प्रकार बनाने के लिए Reflection.Emit का उपयोग किया। प्रत्येक संपत्ति परिभाषा केवल बेस क्लास में शब्दकोश से पढ़ी या लिखी जाती है। चूंकि Reflection.Emit में निम्न-स्तर वाले आईएल कोड लिखने की आवश्यकता है, यह पहले जटिल लगता है। हमने कुछ नमूना व्युत्पन्न कक्षाओं को एक और कक्षा पुस्तकालय में लिखा और उन्हें संकलित किया।ये उदाहरण थे कि हमें वास्तव में रनटाइम पर क्या हासिल करना होगा। फिर हमने ildasm.exe का उपयोग यह देखने के लिए किया कि संकलक किस कोड का उत्पादन करता है। इससे काम करना काफी आसान हो गया कि हम रनटाइम पर एक ही कोड कैसे उत्पन्न कर सकते हैं।

बचना नाम स्थान टकराव

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

यदि यह सर्वर कोड है, तो आपको इस तथ्य पर विचार करने की भी आवश्यकता है कि .NET में असेंबली कभी भी अनलोड नहीं होती है। इसलिए यदि आप बार-बार रनटाइम पर नए प्रकार उत्पन्न कर रहे हैं, तो आपकी प्रक्रिया बढ़ती रहेगी। क्लाइंट कोड में भी ऐसा ही होगा, लेकिन यदि आप एक विस्तारित अवधि के लिए प्रक्रिया को चलाने की अपेक्षा नहीं करते हैं तो यह एक मुद्दा कम हो सकता है।

मैंने कहा कि असेंबली अनलोड नहीं हैं; हालांकि, आप एक संपूर्ण AppDomain को अनलोड कर सकते हैं। तो यदि यह सर्वर कोड है तो आप पूरे ऑपरेशन को अपने स्वयं के एपडोमेन में चला सकते हैं, फिर यह सुनिश्चित करने के लिए गतिशील रूप से बनाए गए प्रकार अनलोड किए जाने के बाद इसे नीचे फाड़ें।

+0

यह वास्तव में समाधान के बहुत करीब है जिसके साथ मैं आया था। मैंने एन <-> एन रिश्ते के साथ 'संपत्ति' और 'डेटाऑब्जेक्ट टाइप' कक्षाएं बनाई हैं। मैंने फिर एक नया 'एक्सटेंशन एस्सेप्लर' बनाने के लिए कोडडॉम कोड जनरेटर का उपयोग किया जो ऊपर की सारणी से एक्सटेंशन गुणों का उपयोग करके नई कक्षाएं बनाएगा। मैंने एक्स्टेंशनकी को प्रत्येक मूल प्रकार के लिए ग्रिड के रूप में संलग्न किया है जो कि संबंधित नए प्रकारों द्वारा पहचानकर्ता के रूप में उपयोग किया जाता है। –

+0

नामकरण संघर्ष से बचने के लिए नए बनाए गए प्रकारों यानी 'उपयोगकर्ता' और 'उपयोगकर्ता एक्सटेंशन' के लिए उपसर्ग या प्रत्यय जोड़ने जितना आसान है। –

0

क्यों नहीं इसकी सभी संपत्तियों के लिए एक महत्वपूर्ण मूल्य जोड़ी का उपयोग करें, या कम से कम गतिशील वाले?

http://msdn.microsoft.com/en-us/library/system.collections.hashtable.aspx

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

+0

क्योंकि ऑर्मेलाइट को उन गुणों के रूप में आवश्यकता है जहां तक ​​मुझे पता है। Htable पाठ –

+0

में क्रमबद्ध किया जाएगा यह मदद कर सकता है .. http://msdn.microsoft.com/en-us/library/ms404245.aspx आप बेस क्लास बना सकते हैं और फिर गतिशील कक्षा बनाने के लिए इसका उपयोग कर सकते हैं क्रम। या आप ठंडा उपयोग प्रतिबिंब। –

0

जिस परियोजना पर मैं वर्तमान में काम कर रहा हूं, उसकी एक समान आवश्यकता है। हमारे पास पहले से ही उत्पादन में एक प्रणाली है और ग्राहक अनुरोध के अतिरिक्त फ़ील्ड हैं।

हमने इसे हमारे मॉडल में कस्टमफिल्ड्स संपत्ति जोड़कर हल किया।

public class Model: IHasId<Guid> 
{ 
    [PrimaryKey] 
    [Index(Unique = true)] 
    public Guid Id { get; set; } 

    // Other Fields... 

    /// <summary> 
    /// A store of extra fields not required by the data model. 
    /// </summary> 
    public Dictionary<string, object> CustomFields { get; set; } 
} 

हम कुछ हफ्तों के लिए इसका उपयोग बिना किसी समस्या के कर रहे हैं।

इससे प्राप्त एक अतिरिक्त लाभ यह था कि प्रत्येक पंक्ति में अपने स्वयं के कस्टम फ़ील्ड हो सकते हैं ताकि हम उन्हें प्रत्येक रिकॉर्ड के लिए आवश्यक रिकॉर्ड के आधार पर प्रति रिकॉर्ड आधार पर संभाल सकें।

+0

स्वीकार करें यदि आपके पास बहुत अधिक फ़ील्ड और मान हैं कि ब्लॉब्ड मान डिफ़ॉल्ट 8000 वर्ण सीमा से अधिक हो जाएगा? –

+0

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

0

ExpandoObject देखें, जो इस तरह कुछ करने के लिए गतिशील भाषा समर्थन प्रदान करता है। आप इसे अपने पीओसीओ के रनटाइम पर अतिरिक्त गुण जोड़ने के लिए उपयोग कर सकते हैं। .NET की DLR सुविधाओं का उपयोग करने पर एक लिंक यहां दिया गया है: http://msdn.microsoft.com/en-us/library/system.dynamic.expandoobject%28v=vs.100%29.aspx

+0

आप केवल Expando ऑब्जेक्ट के उदाहरण में गुण जोड़ सकते हैं। मुझे इस प्रकार के गुण जोड़ने की जरूरत है। –