2012-05-14 19 views
8

मैं एक विकेट वेब एप्लिकेशन बना रहा हूं जिसे कई सारे अनुरोधों को संभालना होगा। मैंने परीक्षण परीक्षण करने के लिए एक परीक्षण वातावरण और कुछ जेमीटर स्क्रिप्ट सेट की हैं और मुझे लगता है कि यदि मैं अधिकतर पेज स्टेटलेस बना देता हूं तो मैं अपने एप्लिकेशन के सीपीयू और मेमोरी पदचिह्न को कम कर सकता हूं।मैं विकेट के "अजाक्सलिंक" स्टेटलेस कैसे बना सकता हूं?

मैंने मुझे यह दिखाने के लिए सबसे बड़े पृष्ठ पर ऑनफ्रेंडर() विधि में कोड जोड़ा है कि कौन से घटक मेरे पृष्ठ को स्टेटफुल कर रहे हैं। इस कोड को मैं पता लगाने के लिए किया है कि:

@Override 
protected void onBeforeRender() {  
    if (!getSession().isTemporary()) { 
     visitChildren(Component.class, new IVisitor<Component>() { 
      @Override 
      public Object component(Component component) { 
       String pageClassName = AbstractStatelessBasePage.this.getClass().getName(); 
       if (!component.isStateless()) { 

        String msg = pageClassName+" is stateful because of stateful component " + component.getClass().getName() + " with id " + component.getId() + "."; 

        List<IBehavior> behaviourList = component.getBehaviors(); 
        for (IBehavior iBehavior : behaviourList) { 
         if (!iBehavior.getStatelessHint(component)) { 
          msg += "\n\t" + "The component has stateful behaviour: " + iBehavior.getClass().getName(); 
         } 
        } 
        LOG.error(msg); 
       } 

       checkedPages.add(pageClassName); 
       return CONTINUE_TRAVERSAL; 
      } 
     }); 
    } 
} 

उत्पादन मुझे लगता है कि स्टेटफुल व्यवहार AjaxLinks पन्नों में मौजूदा घटकों के कुछ लोगों द्वारा इस्तेमाल किया के कारण होता है में:

ERROR - AbstractStatelessBasePage$1.component(45) | HomePage is stateful because of stateful component InfoGrid$InfoButton with id infoButton. 
    The component has stateful behaviour: org.apache.wicket.ajax.markup.html.AjaxLink$1 

मेरे पास है getStatelessHint() विधियों को कुछ स्थानों में "सत्य" लौटने की विधि जोड़ने की कोशिश की, लेकिन ऐसा लगता है कि यह मदद नहीं करता है। मैंने अजाक्सलिंक, इसके सुपरक्लास और आसपास के कोड के विकेट स्रोत कोड की भी जांच की है, लेकिन मुझे लगता है कि अजाक्सलिंक को सभी मामलों में क्यों राज्यिक होना चाहिए।

मेरे मामले में, अजाक्सलिंक अन्यथा स्टेटलेस पेज में है और लिंक राज्य को संग्रहीत नहीं करता है। मैं विकेट को कैसे समझ सकता हूं कि यह अजाक्सलिंक स्टेटलेस हो सकता है?

आपकी मदद के लिए धन्यवाद, रॉल्फ

संपादित करें: स्वीकृत जवाब विकेट 1.4.19 के साथ काम करता है।

जोड़ा गया Maven pom.xml के लिए निम्न:

<dependency> 
    <groupId>com.jolira</groupId> 
    <artifactId>wicket-stateless</artifactId> 
    <version>1.0.8</version> 
</dependency> 

सभी घटकों को जो "AjaxLink" विस्तारित "StatelessAjaxFallbackLink" विस्तार करने के लिए बदल दिया है।

जोड़ने के लिए मत भूलना अपने WicketApplication वर्ग के लिए निम्न, तो यह आपको कुछ समस्या निवारण समय की बचत करेंगे:

@Override 
protected IRequestCycleProcessor newRequestCycleProcessor() { 
    return new StatelessWebRequestCycleProcessor(); 
} 

कृपया ध्यान दें कि StatelessForm और अन्य राज्यविहीन सामान एक पुनरावर्तक के भीतर से काम नहीं करता है (जैसे " ListView ") किसी कारण से।

उत्तर

10

जब आप इसमें अजाक्स व्यवहार जोड़ते हैं तो पृष्ठ राज्यपूर्ण हो जाता है (AjaxLink AjaxEventBehavior का उपयोग करता है)। ऐसा इसलिए है क्योंकि जब आप किसी लिंक पर क्लिक करते हैं तो विकेट सर्वर पर पेज इंस्टेंस खोजने की कोशिश करता है, फिर उसके अंदर लिंक घटक ढूंढें, और आखिरकार इसकी कॉलबैक विधि निष्पादित करें - उदा। क्लिक पर()। पृष्ठ को संग्रहीत किए बिना AJAX व्यवहार उदाहरण को कैसे ढूंढें और इसकी कॉलबैक विधि निष्पादित करने का कोई तरीका नहीं है।

आप जोलीरा के अजाक्स व्यवहार और घटकों (https://github.com/jolira/wicket-stateless) का उपयोग कर सकते हैं।वे थोड़ा अलग काम करते हैं - जब आप जोलीरा के अजाक्सलिंक पर क्लिक करते हैं तो अजाक्स कॉल पृष्ठ का एक बिल्कुल नया उदाहरण बनाता है, इसमें ताजा बनाया गया स्टेटलेसएजैक्सलिंक पाता है, इसकी कॉलबैक विधि निष्पादित करता है, अंत में अजाक्स प्रतिक्रिया के लिए घटकों/जावास्क्रिप्ट को जोड़ने के लिए अजाक्स रिवेस्टटाइटल का उपयोग करता है और नए बनाए गए पेज इंस्टेंस को छोड़ दें (यह कचरा एकत्रित है)। अगला अजाक्स अनुरोध एक बिल्कुल नए पेज उदाहरण के साथ ही करता है।

कोई पूछेगा "क्यों जोलिरा का कोड विकेट कोर में नहीं है?" - क्योंकि यह आंशिक समाधान देता है। उदाहरण के लिए: statelessAjaxLink1 पर क्लिक करना एक नया पृष्ठ बनाता है, StatelessAjaxLink के नए उदाहरण पर ऑनक्लिक() निष्पादित करता है जहां पैनलए को पैनलबी के साथ प्रतिस्थापित किया जाता है, और यह पैनल (पैनलबी) को AjaxRequestTarget में जोड़ता है। संक्षेप में: इस लिंक पर क्लिक करने से पृष्ठ में पैनल के बॉडी को बदल दिया जाता है। यदि पैनलबी में एक स्टेटलेस AJAXLink2 है, तो यह लिंक अविभाज्य है। क्यूं कर ? चूंकि उस पर क्लिक करने से पेज का एक नया उदाहरण बन जाएगा और इस नए इंस्टेंस में पैनलए होगा, पैनलबी नहीं, और इस प्रकार स्टेटक्लेज़एजेक्सलिंक 2 को ऑनक्लिक() विधि निष्पादित करने का कोई तरीका नहीं है।

यदि आपका परिदृश्य काफी सरल है और जोलीरा के घटक आपके मामलों को कवर करते हैं तो उनका उपयोग करें। बस जागरूक रहें कि अधिक जटिल परिदृश्य विफल हो सकता है।

+0

मैं वास्तव में पैनलों को प्रतिस्थापित करता हूं, लेकिन मैं इसे सत्र के भीतर पंजीकृत करता हूं, इसलिए पृष्ठ को तुरंत चालू करते समय मैं सही "प्रतिस्थापित" पैनलों को तुरंत चालू कर सकता हूं। यह पृष्ठ से सत्र तक राज्य चलता है। – Rolf

+0

जोलीरा की स्टेटलेसएजेक्सफॉलबैक लिंक ने मेरे मूल प्रश्न में बताई गई समस्या को हल किया। अभी मुझे स्टेटलेस के अंदर दोहराने वालों के साथ समस्याएं आ रही हैं, जहां विकेट यह पता नहीं लगा सकता कि किस घटक को लक्षित करना है। इसका परिणाम एक नया प्रश्न हो सकता है :-) – Rolf

+0

क्या विकेट 6.10 के लिए कुछ भी है? –

3

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

विकेट 6 के लिए एक समान दृष्टिकोण की कोशिश की गई है, लेकिन लेखक ने इसे प्रयोगात्मक चेतावनी दी है। कोड here है। मैंने इसका उपयोग करने की कोशिश नहीं की है और इस प्रकार इसके लिए झुकाव नहीं कर सकता।

+0

क्या विकेट 6.10 के लिए कुछ भी है? –

+0

@ हेन्डी इरावॉन - मेरा अपडेट देखें! –