jqueryplonekss

How to update a portlet contents periodically?


I'm developing a portlet to show content from several RSS feeds and update them periodically after certain timeout. So I'm studying plone's RSS portlet (plone.app.portlets.portlets.rss).

It uses IDeferredPortletRenderer interface, which look great. They have a method deferred_update() which "refresh portlet data on KSS events (and only then)" that seems to be what I'm looking for. What I'm being unable to find is the KSS call.

Where is the KSS call that updates the RSS portlet? Is this the right approach or should I use jQuery to update the portlet fragment periodically?

Thanks.


Solution

  • You can call the special KSS view @@refreshPortlet for loading portlets over AJAX. The response is a XML document with a <param name="html"> element containing the new HTML snippet. You can call this on the site root or on the current context, whatever works better for your cachability.

    The following is taken from a production site, and is not entirely complete, but should give you an idea:

    // $wrapper is the portlet wrapper div
    var portlethash = $wrapper.attr('id').split('-')[1];
    var base = $wrapper.data('baseurl') || $('link[rel=kss-base-url]').attr('href');
    $.ajax({url: base + '/@@refreshPortlet', type: 'GET', dataType: 'xml',
        data: { portlethash: portlethash },
        success: function(data) {
            var contents = $('dd.portletItem', $(data).find('param[name="html"]').text());
            $wrapper.find('dd.portletItem')
                .replaceWith(contents);
        }
    });
    

    The variable $wrapper refers to the portletWrapper div:

    <div id="portletwrapper-[long string of characters]"
         class="portletWrapper kssattr-portlethash-[long string of characters]">
      <dl class="portlet portletSpecificClass">
        <dt class="portletHeader">
            ...
        </dt>
        <dd class="portletItem">
            ...
        </dd>
        <dd class="portletFooter">
            ...
        </dd>
      </dl>
    </div>
    

    Note that we use the portlet hash from the id attribute, which is how the KSS @@refreshPortlet view knows how to render just the portlet.

    I store the portlet base url on the wrapper in a data attribute in a certain to make sure I retrieve the portlets in the right context as it'd would display the wrong info otherwise.