2014-11-07 5 views
10

असीमित प्रोग्रामिंग के लिए, जर्सी (जेएक्स-आरएस) ConnectionCallback कॉलबैक प्रदान करता है जिसे कनेक्शन टूटने पर निष्पादित किया जाना है। Jersey docs से:AsyncResponse ConnectionCallback जर्सी में आग नहीं है

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

बहुत अच्छा लगता है, लेकिन मैं इसे कभी भी आग में नहीं ले सकता।

@GET 
@Produces(MediaType.TEXT_PLAIN) 
@ManagedAsync 
@Path("/poll") 
public void poll(@Suspended final AsyncResponse asyncResponse) { 
    asyncResponse.register(new CompletionCallback() { 
     @Override 
     public void onComplete(Throwable throwable) { 
      logger.info("onComplete called."); 
     } 
    }); 

    asyncResponse.register(new ConnectionCallback() { 
     @Override 
     public void onDisconnect(AsyncResponse disconnected) { 
      logger.info("onDisconnect called."); 
     } 
    }); 

    asyncResponse.setTimeout(POLL_TIMEOUT_SECONDS, TimeUnit.SECONDS); 
    asyncResponse.setTimeoutHandler(new TimeoutHandler() { 
     @Override 
     public void handleTimeout(AsyncResponse asyncResponse) { 
      logger.info("handleTimeout called."); 
      asyncResponse.resume(Response.status(Response.Status.OK).entity("TIMEOUT").build()); 
     } 
    }); 
} 

अन्य दो कॉलबैक दिखाया गया है, CompletionCallback और TimeoutHandler, आग ठीक, असफल बिना:

यहाँ कुछ कोड है। यदि निर्दिष्ट टाइमआउट अवधि तक पहुंच जाती है, तो टाइमआउटहैंडलर आग लगती है। यदि एक AsyncResponse इंस्टेंस फिर से शुरू किया जाता है, तो CompletionCallback आग लगती है।

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

क्या मुझे कुछ याद आ रही है? क्या जर्नल में कनेक्शन कनेक्शन लागू किया गया है? (यह जेएक्स-आरएस स्पेक में वैकल्पिक है, लेकिन जर्सी डॉक्स इसके बारे में बात करते हैं जैसे कि इसे लागू किया गया है।)

किसी भी इनपुट की सराहना की जाएगी।

उत्तर

4

कनेक्शनकॉल वास्तव में जर्सी में लागू किया गया है। और 'ऑन डिस्कनेक्ट' कॉलबैक भी बुलाया जाता है। आप जर्सी में निम्न कोड पर एक नज़र ले जा सकते हैं:

https://github.com/jersey/jersey/blob/a6ff4d50da13d45ad90fd7375a15a31afa02e489/core-server/src/main/java/org/glassfish/jersey/server/ServerRuntime.java#L723

https://github.com/jersey/jersey/blob/b7907e279010e7035a7a3e529993d22f77a21e08/core-server/src/main/java/org/glassfish/jersey/server/ChunkedOutput.java#L246-L252

ये IOException के मामले में फेंक दिया जाता है, जबकि जवाब लिखते। इसलिए, आपके प्रश्न का उत्तर देने के लिए, कोई मतदान या समान तंत्र नहीं है जो यह जांचता रहता है कि ग्राहक कनेक्ट है या नहीं, पर डिस्कनेक्ट विधि केवल तभी कॉल की जाती है जब आईओएक्सप्शन होता है जो आमतौर पर प्रतिक्रिया लिखते समय होता है।

अद्यतन 1:

इसके अलावा, मैं अपना स्वयं का प्रश्न उद्धृत करने के लिए करना चाहते हैं:

"यह कॉलबैक केवल निष्पादित किया जाएगा यदि कनेक्शन था समय से पहले ही समाप्त या खो जबकि प्रतिक्रिया जा रहा है वापस ग्राहक "

तो, जब तक आप उस पर लिखने की कोशिश करने के लिए लिखा स्ट्रीम, आपका कॉलबैक कभी नहीं निकाल दिया जाएगा।स्पष्ट होने के लिए, जब लिखने की प्रतिक्रिया नहीं होती है या जब प्रतिक्रिया 202 होती है, तो इसका मतलब यह नहीं है कि कनेक्शन को समय-समय पर पर समाप्त कर दिया गया था, जबकि प्रतिक्रिया लिखा जा रहा था।

मुझे डर है कि इस समस्या के लिए कोई समाधान नहीं है जब तक कि आप कुछ प्रकार के मतदान के साथ कुछ निम्न स्तर के नेटवर्क प्रोग्रामिंग लिखते हैं। लेकिन मैं आपको इसके लिए जाने की सलाह नहीं दूंगा।

मेरा सुझाव है कि आप इस विफलता को संभालने के तरीके पर पुनर्विचार करें।

+0

हाय, आपके उत्तर के लिए धन्यवाद। मैंने पहले से ही स्थापित किया था कि इसे जर्सी में लागू किया गया है हालांकि मेरे डीबगिंग में मैं क्लाइंट कनेक्शन को समाप्त करने के विभिन्न माध्यमों के माध्यम से 'ऑन डिस्कनेक्ट' को ट्रिगर करने में सक्षम नहीं था, हालांकि यह पर्यावरण विशिष्ट हो सकता है। इसके अलावा, बक्षीस के लिए, मुझे यह जानना होगा कि इस तथ्य को कैसे संभालना है कि प्रतिक्रिया लिखने का प्रयास करने के बाद डिस्कनेक्ट केवल ऐसा ही प्रतीत होता है, यानी, जब आप अनुरोध को पूरा मानते हैं और जब कोई इकाई नहीं होती है तो इसका संदर्भ क्यों नहीं दिया जाता है लिखने के लिए (पकड़ने की कोशिश केवल इकाई को लिखने के लिए है, 204 के लिए नहीं) – James

+0

अद्यतन के लिए हाय धन्यवाद, भले ही इसे 202 प्रतिक्रिया लिखते समय बुलाया जाना चाहिए क्योंकि यह अभी भी शरीर के बिना भी ग्राहक को प्रतिक्रिया भेज रहा है। जावाडोक कहता है "कंटेनर का पता लगाने के मामले में यह कॉलबैक अधिसूचना विधि लागू की जाती है कि एसिंक्रोनस प्रतिक्रिया से जुड़े रिमोट क्लाइंट कनेक्शन को डिस्कनेक्ट कर दिया गया है।" तो अगर यह अनुरोध पूरा करने के बाद डिस्कनेक्ट पर कॉल करता है (जो मुझे लगता है ठीक है) तो यह नहीं होगा कि एक गैर-शरीर प्रतिक्रिया लिखी जा रही है। – James

+0

मुझे लगता है कि आप कह रहे हैं कि मुझे इसके बारे में सोचने के लिए एक और तरीका चाहिए ... हालांकि मैं वास्तव में एक बाहरी रूप से लगाई गई बाधा को हल करने की कोशिश कर रहा हूं जो केवल खराब एपीआई डिज़ाइन के लिए बनाता है! : एस – James

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