Red Hat
Oct 7, 2013
by Ray Tsang

Simply Awesome!

Context and Dependency Injection (CDI) has been available for a while now – it’s standard with Java EE 6.  Red Hat has always been a steward of open standards and breaking new grounds by leading the specifications, such as leading the CDI specification.  Thus, JBoss Portal 6.1 is proud to bring CDI to Portal applications!

Since standard Java EE 6 applications can now use CDI – why can’t portlets?  CDI offers developer simple, lightweight, container managed options to provide dependency injection.  It’s a great design pattern to follow in any of today’s Java based applications.

The good news is – JBoss Portal 6.1 will support CDI in standard portlets and portlet filters!  All you have to do is to use the already familiar CDI annotations, such as @Inject, or @Produces.

Simply awesome for developers!

How to Use It?

To use CDI in a standard portlet application is extremely easy.  Just like any other CDI-enabled web applications, all you would need to do is to make sure your application contains:

/WEB-INF/beans.xml

The contents of the file, of course, can be extremely simple:

<beans …>
    <!--
    There is nothing here intentionally.
    The existence of this file tells Java EE Container 
    to enable CDI (Contexts and Dependency Injection) 
    for this application.
 -->
</beans>

And that’s all it takes!  Everything behaves just as if you were developing a standard Java EE 6 web application with CDI enabled.

public class MyPortlet extends GenericPortlet {
    @Inject
    private MyService myService;
    ...
}

Portal Specific CDI Scope

CDI standard already specifies a couple of different CDI scopes, such as @RequestScoped, @SessionScoped, @ApplicatioScoped, etc.  Portlets, however, need to deal with additional sophistications such as Portlet Lifecycle – Action phase, and Render phase.

For example, how do you make sure the same bean instance is injected to the portlet across Action phase to Render phase?  A common use case can be that, a user performed an action, and there are associated status message (or error message) that needs to be displayed because of the action.  In essence, this is similar to a Flash Scope pattern in standard web applications.

JBoss Portal 6.1 is introducing two new scopes so developers can focus on the use case and not the underlying technical complexity.

@PortletLifecycleScoped

@PortletLifecycleScoped can be used for the aforementioned use case, where developer needs to provide Flash Scope like functionality.  I.e., the same bean instance will be shared between the Action phase to the subsequent Render phase, and then disposed after the first Render phase.  Subsequent renders will no longer be able to access to that bean instance.

@PortletRedisplayScoped

If, for some reason, that Action-produced result should be long-lived for all of the subsequent renders, then @PortletRedisplayScope can be used!  For example, in the Action phase, you can perform heavy computation to produce the desired result.  The result can be displayed in all of the subsequent render, such as refreshing of the page.

The result will be disposed upon the very next Action phase – and a new instance will then be injected during the Action phase, and the cycle continues.

Serializable

It’s important to remember that for both @PortletLifecycleScoped and @PortletRedisplayScoped beans, the implementation must be Serializable or Externalizable in order to survive across Portlet Lifecyle phases.

MDBlog CDI Example

MDBlog uses CDI heavily for all dependency injection needs.  For example, Resources.java contains most of the producer methods that produces service object instances.  MDBlogPortlet.java injects these services for use.

It’s simple, straightforward, yet very powerful!


Original Post