2016-02-24 5 views
5

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

मेरा सवाल यह है कि सामग्री को पहले ही भेज दिए जाने के बाद ब्राउजर को रीडायरेक्ट करने का कोई तरीका है? इस मामले में, हम <script> टैग की सामग्री को प्रस्तुत करने के बीच में हैं, लेकिन त्रुटि एचटीएमएल में कहीं भी हो सकती है।

मेरे केवल वर्तमान सोचा पेज के शीर्ष पर कुछ जावास्क्रिप्ट इंजेक्षन करने के लिए, और जल्दी से असफल है और उसे बंद कनेक्शन और एक त्रुटि तब होती है जब </body> और </html> टैग जोड़ने के लिए ढांचे के व्यवहार को बदलने की कोशिश करने के लिए है। फिर उपर्युक्त जावास्क्रिप्ट पेजेलोड पर चलाएगा और पता लगाएगा कि पूरे पृष्ठ की सामग्री वहां थी और यदि क्लाइंट-साइड रीडायरेक्ट नहीं करता है तो नहीं। शायद यह पृष्ठ के नीचे एक विशेष छिपा div की तलाश कर सकता है।

क्या इस समस्या को हल करने वाले ढांचे का कोई उदाहरण अलग-अलग या लोगों के इस मुद्दे के आसपास काम कर रहे समान ढांचे का उपयोग कर रहे हैं?

उत्तर

0

मुझे लगता है कि ढांचे को पता नहीं है, लेकिन

http में, हर प्रतिक्रिया एक प्रतिक्रिया-कोड के साथ जुड़े है। चूंकि पृष्ठ पहले से ही आधे रास्ते स्थानांतरित/प्रस्तुत किया गया है कि स्थिति कोड (आमतौर पर "200") पहले ही भेजा गया था (और प्राप्त)।

ब्राउजर के लिए एक और प्रतिक्रिया कोड स्वीकार करने का कोई तरीका नहीं है (जैसे रीडायरेक्ट के लिए "301") उसी प्रतिक्रिया के लिए! इसके अलावा सर्वर एक और प्रतिक्रिया कोड भेजने में सक्षम नहीं है, क्योंकि मूल प्रतिक्रिया कोड पहले से ही पर भेजा गया था और ग्राहक को भेजा गया था।

http-प्रोटोकॉल की त्रुटि और ज्ञान का आपका विवरण यह दर्शाता है कि संभवतः ढांचे/सर्वर घटकों में कुछ कार्यान्वयन त्रुटि है, या यह जानबूझ कर किया गया है, जो स्थिति अब आप जोखिम में है ...

0

किसी पृष्ठ को पुनर्निर्देशित करने के लिए, आपको शीर्षलेख में रीडायरेक्ट जानकारी सेट करने की आवश्यकता है। लेकिन आप शीर्ष लेख लिख सकते हैं एक बार आप सामग्री लेखन शुरू (हो सकता है हेडर पहले से ही समय के आधार पर ग्राहक द्वारा प्राप्त होता है आप पूरे दस्तावेज़ लेखन प्रतिस्पर्धा)

लेकिन, आप नीचे के रूप में अलग तरीके से यह कर सकते हैं

1.let document loading complete and record if you need to redirect the page while rendering 
2. add a unique request-id identifier for each page load 
3. invoke ajax call with request-id (may be rest call) to server asking if page needs to be redirected. 
4. if page needs to be redirected , do so, via javascript in browser at client end. 
0

एक HTTP प्रतिक्रिया में हेडर और वैकल्पिक प्रतिक्रिया सामग्री होती है। सॉकेट कनेक्शन पर प्रतिक्रिया लिखना शुरू करने के बाद आप इसे वापस नहीं कर सकते हैं। आपके उदाहरण में: यदि आप सामग्री पीढ़ी के बीच में कोई त्रुटि चलाते हैं तो आप रीडायरेक्ट हेडर नहीं जोड़ सकते हैं - हेडर सेक्शन पहले ही लिखा जा चुका है।

ऊपर दिया गया बयान पूरी तरह से सत्य नहीं है: HTTP chunked transfer encoding में प्रतिक्रिया अलग-अलग हिस्सों में भेजी जाती है। अंतिम खंड में एक वैकल्पिक ट्रेलर हो सकता है जिसमें इकाई-हेडर फ़ील्ड और सैद्धांतिक रूप से रीडायरेक्ट हेडर हो। लेकिन यदि आप इन तंत्रों का उपयोग कर सकते हैं तो एक अलग सवाल है। उदाहरण के लिए एक सर्वलेट कंटेनर खंडित स्थानांतरण एन्कोडिंग का उपयोग कर सकता है लेकिन ट्रेलर सेट करने के लिए आपको एपीआई नहीं देता है।

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

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

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

ग्राहक पहले से ही एक त्रुटि को संभालने का तीसरा तरीका बताता है, क्लाइंट प्रतिक्रिया को स्वच्छ करता है और कुछ कार्रवाई करता है, त्रुटियों का पता लगाया जाता है (उदाहरण के लिए जेनरेट की गई HTML प्रतिक्रिया में एक स्क्रिप्ट शामिल है)।

+0

अन्य ढांचे इस समस्या को हल कैसे करते हैं? वसंत की तरह, उदाहरण के लिए? प्रतिक्रिया तक लिखने से पहले विचार प्रस्तुत किए जाने तक वसंत वसंत नहीं करता है? या क्या सभी ढांचे में यह समस्या है? – xdhmoore

+0

अंत में @xdhmoore वसंत सर्वलेट प्रौद्योगिकी पर भी आधारित है, और जहां तक ​​मुझे पता है कि मेरे उत्तर में उल्लिखित दूसरी रणनीति का पालन करना है। यह https://spring.io/blog/2013/11/01/exception-handling-in-spring-mvc रुचि का हो सकता है, लेकिन यह मुख्य रूप से एक सार्थक त्रुटि पृष्ठ को प्रेषित करने के तरीके के बारे में है और कैसे बचें या नहीं एक अपवाद से ठीक हो जाओ। – wero

+0

क्या वसंत आपको दृश्य/जेएसपी परत से अपवाद पकड़ने की अनुमति देता है? जहां मैं उलझन में हूं, यह है कि इस ढांचे में हम सभी पिछली सामग्री को लोड करने के बाद अपवाद पर पेज फ्रीज देख रहे हैं।मैंने सोचा था कि स्प्रिंग जैसे अन्य ढांचे ने सामग्री वापस करने से पहले सबकुछ प्रस्तुत किया है (ताकि वे अपवाद के मामले में एक त्रुटि पृष्ठ लौटा सकें), लेकिन यह ढांचा प्रस्तुत करने से पहले सामग्री को वापस करना शुरू कर देता है, जो मुझे लगता है आपका विकल्प 3 केवल एक ही विकल्प से ऊपर ... – xdhmoore

1

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

<script> window.location.href = 'some_new_url';</script> 

एक सरल स्क्रिप्ट टैग मुद्रित कर सकते हैं ब्राउज़र doctype एचटीएमएल से संबंधित कुछ होने को समझता है, तो यह है कि टैग निष्पादित करेंगे।

यदि आप एक बफर में आउटपुट कैप्चर कर सकते हैं, जब आप त्रुटि को संभालते हैं तो आप ब्राउज़र पर HTTP रीडायरेक्ट भेजने का निर्णय ले सकते हैं और उस बिंदु तक आउटपुट बफर को नष्ट कर सकते हैं।

अन्य फ्रेमवर्क के लिए, PHP में, आप केवल ob_start() के साथ आउटपुट बफरिंग सक्षम कर सकते हैं, जो अनुरोध पूरी तरह पूरा होने तक सामग्री भेजना शुरू नहीं करेगा।

0

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

यह HTTP प्रोटोकॉल डिज़ाइन सीमा है कि आउटपुट शुरू होने के बाद आप HTTP रीडायरेक्ट नहीं भेज सकते हैं।

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

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