2008-09-15 14 views
59

मेरे पास एक ऐसा एप्लिकेशन है जो एनएचबीर्नेट को अपने ओआरएम के रूप में उपयोग करता है और कभी-कभी इसे डेटा समस्याओं तक पहुंचने के कारण प्रदर्शन समस्याओं का अनुभव होता है। NHibernate के प्रदर्शन को बेहतर बनाने के लिए किस तरह की चीजें की जा सकती हैं?NHibernate के प्रदर्शन को बेहतर बनाने का सबसे अच्छा तरीका क्या है?

उत्तर

49

पहली और सबसे नाटकीय प्रदर्शन समस्या यह है कि आप NHibernate के साथ में चल सकता है या आप आपके द्वारा बनाए गए हर सत्र के लिए एक नया सत्र कारखाने का निर्माण कर रहे है। प्रत्येक एप्लिकेशन निष्पादन के लिए केवल एक सत्र फैक्ट्री इंस्टेंस बनाया जाना चाहिए और सभी सत्र उस कारखाने द्वारा बनाए जाने चाहिए।

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

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

जो हमें आलसी लोडिंग के विपरीत, लाने के लिए उत्सुक बनाता है। ऑब्जेक्ट पदानुक्रमों या संग्रहों के माध्यम से लूपिंग करते समय, आप कितने प्रश्न बना रहे हैं इसका ट्रैक खोना आसान हो सकता है और आप एक घातीय प्रश्नों के साथ समाप्त हो जाते हैं। एक उत्सव लाने के साथ प्रति प्रश्न आधार पर उत्सुक fetching किया जा सकता है। दुर्लभ परिस्थितियों में, जैसे कि यदि टेबल की एक विशेष जोड़ी है तो आप हमेशा शामिल हो जाते हैं, उस रिश्ते के लिए आलसी लोडिंग को बंद करने पर विचार करें।

हमेशा की तरह, एसक्यूएल प्रोफाइलर प्रश्नों कि धीमी गति से चल रहे हैं या बार-बार किया जा रहा है पता लगाने के लिए एक शानदार तरीका है। मेरे आखिरी नौकरी में हमारे पास एक विकास सुविधा थी जिसने प्रति पृष्ठ अनुरोध के साथ-साथ प्रश्नों की गणना की थी। दिनचर्या के लिए उच्च संख्या में प्रश्न सबसे स्पष्ट संकेतक हैं कि आपका दिनचर्या एनएचबेर्नेट के साथ अच्छी तरह से काम नहीं कर रहा है। यदि प्रतिदिन या अनुरोध प्रति प्रश्न पूछताछ की संख्या अच्छी लगती है, तो आप शायद डेटाबेस ट्यूनिंग के लिए नीचे आ गए हैं; यह सुनिश्चित करना कि आपके पास कैश में निष्पादन योजनाओं और डेटा को संग्रहीत करने के लिए पर्याप्त स्मृति है, अपने डेटा को सही ढंग से अनुक्रमणित करना आदि।

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

+1

है राष्ट्रीय राजमार्ग:

से लिया? यदि नहीं, तो आप इसे मजबूर करने के लिए क्या करते हैं? – sydneyos

+0

@ सिडनीनोस यदि आप फ्लुएंट एनएचबर्ननेट का उपयोग कर रहे हैं, तो आप अपने Fluent NHibernate कॉन्फ़िगरेशन के सम्मेलन के रूप में केवल डिफ़ॉल्ट Lazy.Always() जोड़ सकते हैं। मुझे यकीन नहीं है कि यह एचबीएम मैपिंग के साथ कैसे काम करता है, लेकिन मुझे लगता है कि आप एनएच कॉन्फ़िगरेशन में इसे आसानी से जोड़ सकते हैं। सरल काम उदाहरण और स्पष्टीकरण प्रदान करने के लिए – Anshul

4

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

3

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

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

1

यदि आप पहले से आलसी लोडिंग (उचित रूप से) का उपयोग नहीं कर रहे हैं, तो शुरू करें। जब आपको उनकी आवश्यकता नहीं होती है तो संग्रह प्राप्त करना सब कुछ का अपशिष्ट है।

Chapter Improving performance प्रदर्शन और प्रदर्शन में सुधार के अन्य तरीकों का वर्णन करता है। यहां तक ​​कि साधारण समय इकाई परीक्षण - - पता लगाने के लिए जहां सबसे बड़ी लाभ

संग्रह के लिए बनाया जा सकता है बैच का आकार निर्धारित करने पर विचार जारी चुनिंदा बयानों की संख्या को कम करने के लिए - खंड Improving performance देखने के लिए

1

रूपरेखा पहला कदम है विवरण

1

मुझे केवल एक विकल्प में अपना जवाब सीमित करने की अनुमति है? उस स्थिति में मैं चुनता हूं कि आप एनएचबेर्नेट के दूसरे स्तर के कैश तंत्र को लागू करें।

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

आपका लक्ष्य उन वस्तुओं को परिभाषित करना है जो आपके एप्लिकेशन द्वारा लगातार एक्सेस किए जाते हैं। उनमें से सामान्य सेटिंग्स और पसंद होंगे।

निचले स्तर के दूसरे स्तर के कैश और इसे कार्यान्वित करने के लिए बहुत सारी जानकारी मिलती है।

गुड लक :)

1

कैशिंग, कैशिंग, कैशिंग - आप सही तरीके से अपने पहले के स्तर कैशिंग उपयोग कर रहे हैं [सत्र समय से पहले ही बंद हो रहा है, या प्रथम स्तर कैशिंग बायपास करने के लिए StatelessSession का उपयोग कर]? क्या आपको उन मूल्यों के लिए एक सरल द्वितीय स्तर कैश स्थापित करने की आवश्यकता है जो अक्सर बदलते हैं? क्या आप क्वेरी परिणाम सेट को कैश कर सकते हैं ताकि क्वेरी को तेज़ी से बदल सकें?

[भी कॉन्फ़िगरेशन - क्या आप आइटम को अपरिवर्तनीय के रूप में सेट कर सकते हैं? क्या आप केवल अपनी आवश्यक जानकारी को वापस लाने और उन्हें मूल इकाई में बदलने के लिए प्रश्नों को पुन: व्यवस्थित कर सकते हैं? बांधने से पहले बैटमैन रिडलर को रोकने में सक्षम होगा? ... ओह, माफ करना दूर ले गया]

25

NHibernate के SessionFactory एक महंगी आपरेशन तो एक अच्छी रणनीति एक सिंगलटन जो यह सुनिश्चित करता है कि वहाँ स्मृति में SessionFactory उसमें केवल एक ही बनाता है यह है:।

public class NHibernateSessionManager 
    { 
     private readonly ISessionFactory _sessionFactory; 

     public static readonly NHibernateSessionManager Instance = new NHibernateSessionManager(); 

     private NHibernateSessionManager() 
     { 
      if (_sessionFactory == null) 
      { 
       System.Diagnostics.Debug.WriteLine("Factory was null - creating one"); 
       _sessionFactory = (new Configuration().Configure().BuildSessionFactory()); 
      } 
     } 

     public ISession GetSession() 
     { 
      return _sessionFactory.OpenSession(); 
     } 

     public void Initialize() 
     { 
      ISession disposeMe = Instance.GetSession(); 
     } 
    } 

फिर अपने Global.asax Application_Startup में, आप इसे प्रारंभ कर सकते हैं:

protected void Application_Start() 
{ 
    NHibernateSessionManager.Instance.Initialize(); 
} 
+0

+1। मेरी इच्छा है कि एक अच्छे जवाब के लिए 1 से अधिक देने के लिए सुविधा होगी! –

11

से बचें और/या पहचानने जब आलसी लोड होने से उत्सुक धीमी गति से प्रदर्शन करने वाली क्वेरी के लिए प्राप्त करने में कठिनाई में स्विच करने से Select N + 1 problem को कम।

+0

समाधान पर सहमत नहीं है। आलसी लोडिंग रखें, लेकिन आलसी लोड के [बैच fetching] सक्षम करें (http://nhibernate.info/doc/nhibernate-reference/performance.html#performance-fetching-batch)। यह कोड पर न्यूनतम प्रभाव के साथ एन + 1 समस्या को हटा देता है। मैंने इसके बारे में एक और प्रश्न [यहां] (/ ए/36070727/1178314) के जवाब पर इसके बारे में और लिखा है। –

10

कोई सिफारिश नहीं है लेकिन आपकी मदद करने के लिए एक उपकरण: एनएच प्रोफेसर (http://nhprof.com/) आशाजनक प्रतीत होता है, यह ओआरएम ढांचे के आपके उपयोग का मूल्यांकन कर सकता है। यह NHBernate के अपने चौंकाने वाला एक अच्छा प्रारंभिक बिंदु हो सकता है।

+0

हां। इसे काम करें, फिर इसे तेजी से काम करें। और एनएच प्रोफेसर जैसे प्रोफाइलर आपको बाधा दिखा सकते हैं। –

0

क्या लॉटफ्रीटाइम ने कहा।

प्रलेखन के अध्याय 1 9, "प्रदर्शन में सुधार" पढ़ें।
NHibernate: http://nhibernate.info/doc/nhibernate-reference/performance.html
हाइबरनेट: http://docs.jboss.org/hibernate/core/3.3/reference/en/html/performance.html

उपयोग एसक्यूएल प्रोफाइलर (या डेटाबेस का उपयोग कर रहे के लिए बराबर) लंबे समय से चल प्रश्नों का पता लगाने की। उपयुक्त इंडेक्स के साथ उन प्रश्नों को अनुकूलित करें।

किसी एप्लिकेशन के लगभग हर पृष्ठ पर उपयोग की जाने वाली डेटाबेस कॉल के लिए, एक डेटाबेस क्वेरी से एकाधिक परिणामों को वापस करने के लिए CreateMultiQuery का उपयोग करें।

और बेशक, कैश। पेज/नियंत्रण के लिए आउटपुट कैश निर्देश। डेटा के लिए NHibernate कैशिंग।

+0

वह लिंक अब काम नहीं करता है - किसी के पास एक अपडेटेड लिंक है? – sydneyos

3

"प्रति जवाब एक सिफारिश" केवल? तो मैं इसके लिए जाऊंगा:

डुप्लीकेट्स (एकेए कार्टेशियन उत्पादों) में शामिल होने से बचें क्योंकि दो या दो से अधिक समानांतरों के साथ जुड़ने के कारण; इसके बजाय मौजूदा-उप-सामान, मल्टीक्व्यूरीज़ या FetchMode "उप-चयन" का उपयोग करें। डिफ़ॉल्ट रूप से नहीं आलसी लोड हो रहा है वस्तु के संदर्भ Hibernate Performance Tuning Tips