2009-04-01 18 views
9

मुझे यकीन है कि यह एक सीधा सवाल है, लेकिन निम्नलिखित पर विचार कर रहा हूँ के रूप में विदेशी कुंजी स्तंभ मैप करने के लिए कैसे: मैं कंपनी और क्षेत्र के बीच एक संदर्भ के रूप में निम्नानुसार है:धाराप्रवाह NHibernate - एक संपत्ति

public class Company { 
    public Guid ID { get; set; } 
    public Sector Sector { get; set; } 
    public Guid SectorID { get; set; } 
} 

public class Sector { 
    public Guid ID { get; set; } 
    public string Name { get; set; } 
} 

ठीक है। क्या मैं चाहता हूँ कंपनी वस्तु की SectorID आबादी होने के लिए मैं जाने के बाद है:

(new Company()).Sector = new Sector() { Name="asdf" } 

और एक फ्लश करते हैं।

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

मानचित्रण CompanyMap में मैं वर्तमान में उपयोग कर रहा हूँ

References(c => c.Sector).Cascade.All(); 

किसी को भी किसी भी विचार है है?


आपकी प्रतिक्रिया के लिए धन्यवाद। दुख की बात है अगर मैं दूसरा विकल्प कर (संपत्ति के बराबर हो जाए कॉलम के कॉलम नाम सेट करें, या Map(x => x.SectorID, "Sector_Id") सेट तो मैं त्रुटि मिलती है:

System.IndexOutOfRangeException: गणना के साथ इस SqlParameterCollection के लिए अमान्य सूचकांक 7 = 7.

मुझे पहला विकल्प करना पड़ सकता है लेकिन मुझे चिंता है कि जब आप सेक्टर आईडी को कॉल करते हैं तो एक अतिरिक्त क्वेरी निकाल दी जाएगी क्योंकि यह सेक्टर स्वयं डीबी से बाहर हो जाता है (जब तक यह उत्सुक लोड न हो जाए परेशानी का थोड़ा सा)

मुझे आश्चर्य है कि इसका कोई आसान जवाब नहीं है।


वाह! अगर मैं

public virtual Guid SectorID 
{ 
    get { return Sector.ID; 
} 

का उपयोग तो nhibernate काफी चतुर को पता है कि संगठन क्वेरी में Sector_id स्तंभ वास्तव में Sector.ID के समान है है और यह फन के तहत इस देता है। यदि आप आलसी लोड करते हैं तो भी यह एक अतिरिक्त क्वेरी नहीं भेजता है। मैं प्रभावित हु!


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

उत्तर

2

दो विचार: सबसे पहले, ऐसा कुछ नहीं होगा जो आप चाहते हैं?

public class Company { 
    public Guid ID { get; set; } 
    public Sector Sector { get; set; } 
    public Guid SectorID { 
     get { return Section.ID; } 
     // Really not sure what behavior your setter should have here; Maybe it shouldn't even have one? 
     set { Sector = new Sector { ID = value }; } 
    } 
} 

दूसरा, जब आप कहते हैं कि मानचित्रण डीबी में एक स्तंभ बनाया Sector_Id कहा जाता है, कि एक कॉलम के अलावा है कि आप SectorID नाम बनाया है?यदि ऐसा है, तो आप कॉलम नाम बदल सकते हैं, इसलिए यह सही नाम (here's the documentation for mappings का उपयोग करता है, "कॉलम नाम निर्दिष्ट करना" नीचे कुछ शीर्षलेख देखें)।

इसके अलावा, क्या आप सेक्टर आईडी संपत्ति का मानचित्रण कर रहे हैं (उदाहरण के लिए। "मानचित्र (x => x.SectorID," Sector_Id ")")?

2

स्टीव आपको पीओसीओ कक्षा में विदेशीकी संपत्ति की आवश्यकता नहीं है।

उदाहरण के लिए यदि आप लेख लेखक की आईडी प्राप्त करने का प्रयास करेंगे तो कोई भी चयन नहीं किया जाएगा।

वर authorID = Article.Author.ID

13

यह आसानी से एक सूत्र संपत्ति के साथ किया जाता है।

public class Company { 
    public virtual Guid Id { get; set; } 
    public virtual Guid? SectorId { get; set; } 
    public virtual Sector Sector { get; set; } 
} 

public class CompanyMap : ClassMap<Company> { 
    public CompanyMap() { 
    Id(x => x.Id); // Maps to a column named "Id" 
    References(x => x.Sector); // Maps to a column named "Sector_id", unless you change the NHibernate default mapping rules. 
    Map(x => x.SectorId).Formula("[Sector_id]"); 
    }  
} 

यह वास्तव में कार्य करना चाहिए कि आप कैसे चाहते हैं। जब Company नया है, SectorId शून्य होगा; जब Company डीबी से प्राप्त किया जाता है, SectorId दिए गए फॉर्मूला मान के साथ पॉप्युलेट किया जाएगा। SectorId को एक संपत्ति के रूप में उजागर किया गया है, जो वेब ड्रॉप डाउन आदि से निपटने के लिए वास्तव में अच्छा बनाता है। जब आप सहेजते हैं, तो आपको अभी भी "असली" एसोसिएशन को बांधना होगा। यह मानते हुए कि SectorId एक रूप में चयनित किया गया था ...

using (var txn = session.BeginTransaction()) { 
    // Set the FK reference. 
    company.Sector = session.Load<Sector>(company.SectorId); 
    // Save the new record. 
    session.Save(company); 
    // Commit the transaction. 
    txn.Commit(); 
} 
+0

मैं त्रुटि मैं हो रही थी को सुलझाने के लिए आप अंक दे, लेकिन यह पूरी तरह से गैर सहज लगता है। यह NHibernate में एक डिज़ाइन समस्या की तरह प्रतीत होता है यदि यह ऐसी सामान्य परिदृश्य को संभाल नहीं सकता है क्योंकि दोनों एफके आईडी और संबंधित ऑब्जेक्ट-इंस्टेंस दोनों गुणों के रूप में हैं। –

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