Introduction

Once a portlet is placed on a portal page, its data is not directly shared with other portlets. IPC (Inter Portlet Communication) defines the ways that a Portlet can interact and communicate with another Portlet. There are four ways to make inter portlet communication :

Events

JSR 286 (Portlet 2.0) introduced portlet communication using events. Due to JSF life cycle communication between JSF portlets is made differently in comparison to MVCPortlet.

There is no direct alignement between Portlet event phase and any JSF lifecycle phase. Javax.portlet specification introduced an event bridge to process portlet events. Below steps to follow to make a JSF Portlet communication using events:

Defining the event in the Portlet.xml

The first step is to define the event that will be fired and processed by portlets. The definition is set in the portlet configuration file Portlet.xml. Below the declaration:

1

2

3

4

<event-definition xmlns:event="http://www.namespace.com">

<qname>identifier</qname>

<value-type>java.lang.String</value-type>

</event-definition>

Xmlns : Give a namespace to the eventQname : Give a unique identifier in the namespaceValue-type : Type of object the event will transfere

Create a bridge event handler

To handle portlet events, you must create a custom bridge event handler which will process all events fired by portlets that defined it. In fact, you must create a Java class that implements the handleEventmethod of javax.portlet.faces.BridgeEventHandler interface as below :

We will implement this method to process the event in the receiver portlet.

Sender portlet

Declare that the sender portlet is publishing the defined event in portlet.xml

To send the event, the portlet must specify that it’s publishing it. Add in portlet.xml file the <supported-publishing-event> property that refers to the event identifier. Example:

1

2

3

4

5

6

7

<portlet>

...

<supported-publishing-event xmlns:event="http://www.namespace.com">

<qname>identifier</qname>

</supported-publishing-event>

...

</portlet>

Xmlns must be the same as the event definition. Same for the event identifier.

Declare the custom bridge handler in the portlet.xml

The event sender portlet must register the custom bridge event handler that will process the event. To do so, you must give the fully qualified name of the bridge event handler created in the previous section. Let’s consider that it is located in the package : com.roufid.tutorials.bridge. Below the configuration :

1

2

3

4

5

6

7

8

<portlet>

...

<init-param>

<name>javax.portlet.faces.bridgeEventHandler</name>

<value>com.roufid.tutorials.bridge.CustomBridgeEventHandler</value>

</init-param>

...

</portlet>

Firing the event

Firing event from the sender portlet is done by using QName class that refers to the defined event by giving its namespace and identifier.

Receiver portlet

Declare that the portlet is processing the defined event in portlet.xml

The receiver portlet must declare that it’s processing the defined event by adding the property <supported-processing-event> in the portlet.xml

1

2

3

<supported-processing-event>

<qname xmlns:x="http://www.namespace.com">identifier</qname>

</supported-processing-event>

Declare the custom bridge handler in the portlet.xml

Same as the sender portlet, the receiver portlet must register the custom bridge event handler. Define the same configuration :

1

2

3

4

5

6

7

8

<portlet>

...

<init-param>

<name>javax.portlet.faces.bridgeEventHandler</name>

<value>com.roufid.tutorials.bridge.CustomBridgeEventHandler</value>

</init-param>

...

</portlet>

Processing the fired event in the CustomBridgeEventHandler

Processing the fired event is done in the CustomBridgeEventHandler you created previously. Since this CustomBridgeEventHandler is processing all fired events you must distinguish them. To do so, you can check the fired event QName as below :

Concrete example

CarList (Sender Portlet): This portlet shows a list of cars. The user can select a car from the list. When the user select a car, an event will be fired with the selected car identifier. The car information will be displayed in the second portlet.

CarInformation (Receiver Portlet):If an event is fired, it will be processed in the second portlet which will display the car information.

JSF portlet communication using event

Defining the event

The first step is to define the event that will be fired and processed by portlets in the portlet.xml file. If the portlets that handle the event are in the same Liferay Plugin Project, so only one definition of the event must be in the portlet.xml file. If not, each Liferay plugin project must declare it in its portlet.xml file.

In this example, the two portlets are in the same Liferay Plugin Project.

The event that will be fired and processed will be called “selectCarEvent” and will store the car identifier which is a java.lang.String. The declaration is as following :

1

2

3

4

5

<!-- Defining the event -->

<event-definition xmlns:event="http://www.roufid.com">

<qname>event:selectCarEvent</qname>

<value-type>java.lang.String</value-type>

</event-definition>

Defining the event handler : CarBridgeEventHandler

Below the bridge that will handle portlet events.

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

/**

* Event handler which will process all Portlet events.

*

* @author Radouane ROUFID.

*

*/

publicclassCarBridgeEventHandlerimplementsBridgeEventHandler{

@Override

publicEventNavigationResult handleEvent(FacesContext facesContext,

Event event){

EventNavigationResult eventNavigationResult=null;

// Processing the event will be here...

returneventNavigationResult;

}

}

Sender portlet : CarList

Portlet.xml

Defining the CarList portlet in the portlet.xml file. This portlet will publish the “selectCarEvent” event. It must define the <supported-publishing-event> property :