February 24, 2021
Hot Topics:

Reusable Syndicated Media Portlets: An Example of Simplified Content Presentation

  • By Scott Nelson
  • Send Email »
  • More Articles »

In the early days of the World Wide Web, the battle cry of successful sites was "Content is king!" Web pages needed to be content heavy to gain rankings on the search engines and draw visitors, and the content needed to be updated regularly to bring those visitors back. As the technology evolved and business models changed, functionality and interactivity gained importance in capturing clicks. Portals provide the most manageable framework for organizing and presenting both functionality and content. But, "most manageable" isn't the same is "easily manageable" and content is still a key part of a successful portal. For portal developers and administrators, this means that the content for a portal will grow, both in source and type.

Managing Content Growth

All portal frameworks either include a content management system (CMS) or provide an interface to popular CMS applications (or both). CMS is an important topic of its own, and in some case the CMS approach will be all that you need. Or, you may have an external content provider, many of which provide presentation capabilities as well. RSS feeds, blogging, and wiki frameworks are also sources of content. Each of these content sources generally provides some method of presentation that can be used out-of-the-box (OOTB).

Sometimes, the presentation that comes OOTB doesn't fit your requirements. In that case, you need to build custom portlets to render the content. The usual approach is to build a complete portlet for each presentation. For the sake of semantics, let me define a complete portlet as minimally consisting of a DAO, a controller, a JSP, and a portlet configuration file (frequently includes a delegate class as well). For one content portlet, this isn't so much work and is fairly easy to manage. But, for three portlets—that is, 12 to 16 files and a completely new deployment for each additional portlet—it doesn't take long for this to become unwieldy.

For some reason, reuse isn't often applied to these types of situations. Because the content is different for each of these presentations, it is frequently considered a given that the solution needs to be different. Of course, "frequently" doesn't mean "always" and there are probably many other solutions than what will be demonstrated in this article (yes, that is four non-specific qualifiers in the same sentence).

One Solution to Many Content Portlets

Let me start with some specific qualifiers to clarify the intent and approach of this solution. The code snippets, IDE references, and framework naming conventions used in this article are based on the WebLogic Portal. The approach will work on any JSR-168 or JSR 286 compliant portal framework, only some of the base classes and file extensions may need to be modified. However, because the examples are built on WLP, some WLP-specific tips will be included and noted as such.

Note: The examples are not fully production-level in that they do not include robust error handling and do use string literals where static final values would provide far better performance. Please be sure to address this if you adapt this example to your own solution.

The data model used for the examples is XML, and the DAO object is a static dummy bean because this article is based on a real-world example where that part of the code is proprietary and the data source is irrelevant to the solution. That dummy object always doubles as a delegate.

Using a delegate class in this approach will allow you the highest level of reuse. Your delegate can expose an interface for your controller that is consistent for content in general. Then, no matter what your content source or format is, the delegate can abstract away all of the differences, returning it to your controller with a single method signature.

Take an iterative approach to building your content portlet, making the first step to simply fetch and display some content. Because your delegate is abstracting the nature of the content to a single method call, youcan start with a simple portlet controller:

public Forward begin()
   Forward forward = new Forward("default");
   List<String> contentDocList = new ArrayList<String>();

   forward.addActionOutput("contentDocList", contentDocList);

   return forward;

The content is set into a list to provide for the possibility of multiple calls to getSyndicatedContent for different content types of the same format, such as general news type that has multiple categories.

The choice of using a PageFlow controller above is based on it being the fastest way to build a portlet in Workshop. This leads to your first WebLogic-specific note.

WebLogic-Specific Note: PageFlow controls from at least version 9.2 are stored in the session; this makes this solution a major resource saver as well. The use of action output is also for the sake of speed. It could just easily be request attribute or a bean field.

Skipping the basic JSP elements and field declarations, the content then can be rendered with the following:

saxBuilder = new SAXBuilder();
formatPath = (String)pageContext.getAttribute("contentType");
docListIt  = contentDocList.iterator();
   stringReader  = new StringReader(docListIt.next());
   document      = saxBuilder.build(stringReader);
   contentList   = document.getRootElement().getChildren();
   contentListIt = contentList.iterator();
<%//assume if only one category there we don't need the heading.
   <span style ="margin-left:10px" id =
       replace(" ", "") %>_heading">
       <%=contentList.get(0).getChildText("category") %></span>
       <%} %>
   <ul style = "margin-top:0; margin-right:10px"
       id = "<%=contentList.get(0).getChildText("category") %>
<% while(contentListIt.hasNext())
      contentElement = contentListIt.next();%>
         <a href = "<%=contentElement.getChildText("url") %>"
         target = "_blank">
         <%=contentElement.getChildText("headline") %></a>
<%     } %></ul>

Page 1 of 3

This article was originally published on July 22, 2008

Enterprise Development Update

Don't miss an article. Subscribe to our newsletter below.

Thanks for your registration, follow us on our social networks to keep up-to-date