क्या है यह स्प्रिंग.जापा.पेन-इन-व्यू = स्प्रिंग बूट में सच्ची संपत्ति?


121

मैंने spring.jpa.open-in-view=trueजेपीए विन्यास के लिए स्प्रिंग बूट प्रलेखन में संपत्ति देखी ।

  • है trueइस संपत्ति के लिए डिफ़ॉल्ट मान है, तो यह सब पर से उपलब्ध नहीं है ?;
  • यह वास्तव में क्या करता है? मुझे इसके लिए कोई अच्छी व्याख्या नहीं मिली;
  • क्या यह आप के SessionFactoryबजाय का उपयोग करता है EntityManagerFactory? यदि हाँ, तो मैं यह कैसे बता सकता हूं कि मुझे EntityManagerFactoryइसके बजाय उपयोग करने की अनुमति है ?

धन्यवाद!

जवाबों:


52

यह गुण एक पंजीकृत करेगा OpenEntityManagerInViewInterceptor, जो EntityManagerवर्तमान थ्रेड को पंजीकृत करता है, इसलिए आपके पास EntityManagerवेब अनुरोध समाप्त होने तक ऐसा ही रहेगा। इसका हाइबरनेट SessionFactoryआदि से कोई लेना-देना नहीं है ।


फिलहाल मेरे पास OpenEntityManagerInViewFilter फ़िल्टर है, जो EntityManager को नियंत्रित करने के लिए वेब अनुरोध पूरा होने तक है। इस इंटरसेप्टर का अर्थ था "OpenEntityManagerInViewInterceptor" वही है जो "OpenEntityManagerInViewFilter" है? उनके बीच क्या अंतर है? तो, मैं स्प्रिंग बूट के लिए अपने सर्वलेट संदर्भ में इस फ़िल्टर को और अधिक नहीं करूंगा?
कार्लोस अल्बर्टो

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

299

OSIV एंटी-पैटर्न

व्यापार परत को यह तय करने के बजाय कि व्यू लेयर द्वारा आवश्यक सभी संघों को कैसे प्राप्त करना सबसे अच्छा है, OSIV (ओपन सेशन इन व्यू) दृढ़ता के संदर्भ में खुले रहने के लिए बाध्य करता है, ताकि दृश्य परत प्रॉक्सी आरंभीकरण को ट्रिगर कर सके, जैसा कि सचित्र है निम्नलिखित चित्र द्वारा।

यहां छवि विवरण दर्ज करें

  • OpenSessionInViewFilterकॉल openSessionअंतर्निहित की विधि SessionFactoryऔर एक नया प्राप्त Session
  • के Sessionलिए बाध्य है TransactionSynchronizationManager
  • OpenSessionInViewFilterकॉल doFilterकी javax.servlet.FilterChainवस्तु संदर्भ और अनुरोध आगे संसाधित किया जाता है
  • DispatcherServletकहा जाता है, और अंतर्निहित करने के लिए इसे मार्गों HTTP अनुरोध PostController
  • PostControllerकॉल PostServiceकी एक सूची प्राप्त करने के लिए Postसंस्थाओं।
  • PostServiceएक नई लेन-देन को खोलता है, और HibernateTransactionManagerएक ही पुनः उपयोग कर लेता Sessionहै कि द्वारा खोला गया था OpenSessionInViewFilter
  • PostDAOकी सूची को हासिल करेगा Postकिसी भी आलसी संघ आरंभ बिना संस्थाओं।
  • PostServiceअंतर्निहित लेन-देन करता है, लेकिन Sessionबंद नहीं है, क्योंकि यह बाह्य खोला गया था।
  • DispatcherServletशुरू होता है यूआई, जो, बारी में, आलसी संघों नेविगेट करता है और उनके प्रारंभ से चलाता है प्रतिपादन।
  • OpenSessionInViewFilterबंद कर सकते हैं Session, और अंतर्निहित डेटाबेस कनेक्शन में अच्छी तरह से जारी किया गया है।

पहली नज़र में, यह करने के लिए एक भयानक बात की तरह नहीं लग सकता है, लेकिन, एक बार जब आप इसे डेटाबेस के दृष्टिकोण से देखते हैं, तो दोषों की एक श्रृंखला अधिक स्पष्ट होने लगती है।

सेवा परत डेटाबेस लेनदेन को खोलता और बंद करता है, लेकिन बाद में, कोई स्पष्ट लेनदेन नहीं होता है। इस कारण से, UI रेंडरिंग चरण से जारी किए गए प्रत्येक अतिरिक्त विवरण को ऑटो-कमिट मोड में निष्पादित किया जाता है। ऑटो-कमेट डेटाबेस सर्वर पर दबाव डालता है क्योंकि प्रत्येक स्टेटमेंट में ट्रांजेक्शन लॉग को डिस्क में फ्लश करना चाहिए, इसलिए डेटाबेस साइड पर बहुत सारे I / O ट्रैफिक का कारण बनता है। एक अनुकूलन के Connectionरूप में केवल पढ़ने के लिए चिह्नित किया जाएगा जो डेटाबेस सर्वर को लेनदेन लॉग में लिखने से बचने की अनुमति देगा।

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

यूआई परत नेविगेट करने वाले संघों तक सीमित है, जो बदले में, एन + 1 क्वेरी समस्याओं को ट्रिगर कर सकती है । यद्यपि हाइबरनेट @BatchSizeबैचों में संघों को लाने के लिए प्रदान करता है , और FetchMode.SUBSELECTइस परिदृश्य के साथ सामना करने के लिए, एनोटेशन डिफ़ॉल्ट रूप से लाने की योजना को प्रभावित कर रहे हैं, इसलिए वे हर व्यवसाय उपयोग के मामले में लागू होते हैं। इस कारण से, डेटा एक्सेस लेयर क्वेरी बहुत अधिक उपयुक्त है क्योंकि इसे वर्तमान उपयोग के मामले में डेटा की आवश्यकताओं के अनुरूप बनाया जा सकता है।

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

स्प्रिंग बूट और OSIV

दुर्भाग्य से, OSIV (ओपन सेशन इन व्यू) स्प्रिंग बूट में डिफ़ॉल्ट रूप से सक्षम है , और OSIV वास्तव में एक प्रदर्शन और मापनीयता के दृष्टिकोण से एक बुरा विचार है

इसलिए, सुनिश्चित करें कि application.propertiesकॉन्फ़िगरेशन फ़ाइल में, आपके पास निम्न प्रविष्टि है:

spring.jpa.open-in-view=false

यह OSIV को अक्षम कर देगा ताकि आप सही तरीके से संभालLazyInitializationException सकें ।

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

OSIV के बारे में अधिक जानकारी के लिए, इस लेख को देखें


14
आजकल एक लॉग इन किया जा रहा है।
व्लाद मिहालसी

क्या यह सामान्य रूप से स्प्रिंग पर लागू होता है, या केवल स्प्रिंग बूट पर? क्या प्रॉपर्टी सेट करने के बजाय @ कॉन्फ़िगरेशन-एनोटेट वर्ग के माध्यम से इसे अक्षम किया जा सकता है?
गॉर्डन

2
यह केवल स्प्रिंग बूट पर लागू होता है। मानक वसंत में, आप स्पष्ट रूप से चुनते हैं कि किन बीन्स का उपयोग करना है या क्या आप एक वेब फ़िल्टर चाहते हैं, जैसे कि OSIV। मुझे नहीं पता कि क्या आप इसे कुछ एनोटेशन के माध्यम से अक्षम कर सकते हैं। मुझे केवल कॉन्फ़िगरेशन सेटिंग का पता है।
व्लाद मिहालसी

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

5
विकिपीडिया के अनुसार, "एक विरोधी पैटर्न एक आवर्ती समस्या के लिए एक सामान्य प्रतिक्रिया है जो आमतौर पर अप्रभावी होती है और जोखिम अत्यधिक प्रतिशोधी होते हैं"। ठीक यही दृश्य में ओपन सेशन है।
व्लाद मिहालसी
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.