2012-08-30 10 views
10

के बीच में सुपर क्लास मैप किया गया इस प्रकार मैं वर्तमान में एक मॉडल संरचना है:Symfony2/सिद्धांत वर्ग तालिका विरासत

/** 
* @ORM\Entity 
* @ORM\InheritanceType("JOINED") 
* @ORM\DiscriminatorColumn(name="related_type", type="string") 
* @ORM\DiscriminatorMap({"type_one"="TypeOne", "type_two"="TypeTwo"}) 
*/ 
abstract class BaseEntity { 

    ... (all the usual stuff, IDs, etc) 

    /** 
    * @ORM\OneToMany(targetEntity="Comment", mappedBy="baseEntity") 
    */ 
    private $comments; 
} 

/** 
* @ORM\Entity 
*/ 
class TypeOne extends BaseEntity { 
    /** 
    * @ORM\Column(type="string") 
    */ 
    private $name; 

    /** 
    * @ORM\Column(type="string") 
    */ 
    private $description; 
} 

/** 
* @ORM\Entity 
*/ 
class TypeTwo extends BaseEntity { 
    /** 
    * @ORM\Column(type="string") 
    */ 
    private $name; 

    /** 
    * @ORM\Column(type="string") 
    */ 
    private $description; 
} 

/** 
* @ORM\Entity 
*/ 
class Comment { 

    ... (all the usual stuff, IDs, etc) 

    /** 
    * @ORM\ManyToOne(targetEntity="BaseEntity", inversedBy="comments") 
    */ 
    private $baseEntity; 
} 

विचार यहाँ अन्य तालिकाओं में से किसी के लिए एक टिप्पणी टाई करने में सक्षम होना है। यह सब अभी तक ठीक काम कर रहा है (मान लीजिए, मैं अभी भी डिज़ाइन विकल्पों की खोज कर रहा हूं इसलिए ऐसा करने का एक बेहतर तरीका हो सकता है ...), लेकिन एक बात मैंने देखी है कि उप-वर्गों में कुछ सामान्य फ़ील्ड हैं कि मैं एक सामान्य माता-पिता वर्ग में जाना चाहता हूं। मैं उन्हें बेसइन्टिटी में नहीं ले जाना चाहता क्योंकि वहां अन्य वस्तुएं होंगी जो बेसइन्टिटी के बच्चे हैं, लेकिन उनमें उन फ़ील्ड नहीं होंगे।

मैं बहुत की तरह, बीच में एक MappedSuperclass माता पिता वर्ग बनाने पर विचार किया है:

/** 
* @ORM\MappedSuperclass 
*/ 
abstract class Common extends BaseEntity { 
    /** 
    * @ORM\Column(type="string") 
    */ 
    private $name; 

    /** 
    * @ORM\Column(type="string") 
    */ 
    private $description;  
} 

/** 
* @ORM\Entity 
*/ 
class TypeOne extends Common {} 

/** 
* @ORM\Entity 
*/ 
class TypeTwo extends Common {} 

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

उत्तर

14

डॉक्स से:

एक मैप किए गए सुपर क्लास एक अमूर्त या ठोस वर्ग है कि इसके उपवर्गों के लिए लगातार इकाई राज्य और मैपिंग जानकारी, प्रदान करता है, लेकिन जो अपने आप में एक इकाई नहीं है। आमतौर पर, मैप किए गए सुपरक्लास का उद्देश्य राज्य और मैपिंग जानकारी को परिभाषित करना है जो एकाधिक इकाई वर्गों के लिए आम है।

उस ने कहा, आप एक इकाई को उस व्यक्ति के साथ कैसे जोड़ सकते हैं जो नहीं है?

डॉक्स से अधिक:

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

स्रोत: http://docs.doctrine-project.org/projects/doctrine-orm/en/latest/reference/inheritance-mapping.html


अद्यतन

क्योंकि आपके MappedSuperClass फैली BaseEntity यह भी BaseEntity के संघों को विरासत के रूप में अगर यह अपने आप ही थे। तो आप प्रभावी ढंग से एक मैपडप्पर क्लास पर OneToMany है।

इसके आस-पास पहुंचने के लिए, आपको जिस तरीके से काम करना है, उसे काम करने के लिए आपको संशोधित/विस्तार करने की आवश्यकता होगी।

जहाँ तक देशी कार्यक्षमता चला जाता है के रूप में आप दो विकल्प हैं:

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

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

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

यदि आपका डेटा उस उदाहरण का पालन करता है तो एकल तालिका या कक्षा तालिका विरासत के साथ जाएं। यदि नहीं, तो मैं फ़ील्ड को समूहबद्ध करने की सलाह नहीं दे सकता हूं।

+0

मैं समझता हूं कि एक मैप किए गए सुपरक्लास पर एक से कई संगठन संभव नहीं हैं ... हालांकि मेरा परिदृश्य थोड़ा अलग है। मेरी प्रस्तावित संरचना बेसइन्टिटी (एक वास्तविक इकाई) है -> मैप्डसुपरक्लास -> ग्रैंडचिल्डेरेंटिटीज (संस्थाएं)। एक से कई एसोसिएशन बेसइन्टिटी और दूसरी इकाई के बीच है। तो तकनीकी रूप से, एसोसिएशन मैप किए गए सुपरपरक्लास के लिए नहीं है क्योंकि मैप किए गए सुपरक्लास बेसएन्टीटी का एक बच्चा है और इसमें एक से कई एसोसिएशन शामिल नहीं हैं। – cdwhatcott

+0

अद्यतन के लिए धन्यवाद मेरे अद्यतन उत्तर – KTastrophy

+0

देखें। कुछ चीजों पर काम करने में कुछ समय बिताया और फिर इस समस्या पर वापस आकर, मुझे लगता है कि सबसे अच्छा विकल्प 'सामान्य' को एक इकाई बनाने जैसा होगा जैसा आप सुझाव देते हैं। – cdwhatcott