Portlets - JSR168

Fabrice SZNAJDERMAN

Cet article est une première approche du concept des portlets. Il permet d'avoir une vision générale sur le fonctionnement, l'architecture et les objectifs de ces composants.

- Titre : Portlets - JSR168

- Auteur : Fabrice SZNAJDERMAN

- Parution : 14 mars 2007

- Mise à jour : 10 février 2020

- Licence : Les sources présentées sur cette page sont libres de droits et vous pouvez les utiliser à votre convenance. Par contre, la page de présentation constitue une œuvre intellectuelle protégée par les droits d'auteur. Copyright ® 2013 Fabrice SZNAJDERMAN. Aucune reproduction, même partielle, ne peut être faite de ce site et de l'ensemble de son contenu : textes, documents, images, etc. sans l'autorisation expresse de l'auteur. Sinon vous encourez selon la loi jusqu'à trois ans de prison et jusqu'à 300 000 € de dommages et intérêts.

Sommaire

- I. Introduction

- I-A. Définition d'un portlet

- I-B. Qu'est-ce qu'un portail ?

- I-C. Objectif

- II. Portlet et servlet

- II-A. Les points communs

- II-B. 2.4. Les points de divergences

- III. Description d'un portlet

- III-A. Arborescence des fichiers

- III-B. Le fichier portlet.xml

- IV. Le cycle de vie d'un portlet

- IV-A. Phase d'initialisation

- IV-B. Diagramme de séquence

- V. Les méthodes

- V-A. Init (portletConfig portletConfig)

- V-B. Render (RenderRequest rRequest, RenderResponse rResponse)

- V-C. Destroy()

- VI. Mode et état d'un portlet

- VI-A. Mode

- VI-A-1. VIEW

- VI-A-2. EDIT

- VI-A-3. HELP

- VI-B. États

- VI-B-1. CLOSE

- VII. Informations diverses

- VII-A. Les acteurs

- VII-B. Les API

- VIII. Tutoriel

- VIII-A. Prérequis

- VIII-B. Installation de JBossPortal

- VIII-B-1. Téléchargement

- VIII-B-2. Démarrage et arrêt du serveur

- VIII-B-3. Vérification de l'installation

- VIII-C. Installation de NetBeans

- VIII-C-1. Téléchargement

- VIII-C-2. Installation du plugin

- VIII-D. Création du portlet : HelloWorldportlet

- VIII-D-1. Création du projet : HelloWorldProject

- VIII-E. Déploiement et affichage du portlet

- VIII-E-1. Déploiement du portlet

- VIII-F. Paramétrage du portail

- VIII-F-1. Création d'une page

- VIII-F-2. Ajout de portlets

- IX. Conclusion

- X. Remerciements

I - Introduction

I-A - Définition d'un portlet

Un portlet est un composant web unitaire s'intégrant au sein d'un conteneur (portail).

Chaque portlet est indépendant des autres et peut-être imaginé comme une application WEB au sens J2EE (d'où l'idée de composant web unitaire).

Les portlets se basent sur une API définie par la spécification JSR 168.

Cette spécification étend (ou duplique) l'API des servlets.

Il existe une grande similarité entre les Servlets et les portlets. Nous verrons un peu plus loin ces différences.

I-B - Qu'est-ce qu'un portail ?

D'un point de vue technique un portail est un conteneur.

Ce conteneur manipule les portlets, le portail fournit aux portlets un environnement d'exécution.

Il les positionne sur les pages, il gère leur cycle de vie, etc.

D'un point de vue fonctionnel un portail est une application web permettant d'agréger du contenu.

Il permet de centraliser différentes sources d'information sur une unique page.

Chaque source d'information est représentée par un portlet.

Le conteneur, hébergeant les portlets a la responsabilité de fournir un environnement d'exécution aux portlets.

I-C - Objectif

La spécification JSR168 a pour objectif de standardiser les portlets et d'assurer une interopérabilité entre les différents portails du marché.

Aussi, chaque fournisseur a adapté et spécialisé cette spécification. Je pense par exemple à IBM et le portail WebSphere-Portal qui fournit une API propre à ce serveur (les versions récentes du portail abandonnent cette API spécifique pour rentrer dans les standards).

Le but de cet article est de donner une vue générale sur les portlets.

II - Portlet et servlet

Afin de mieux appréhender le fonctionnement des portlets, je vais vous présenter les points communs et les points de divergence entre ces deux composants.

II-A - Les points communs

Voici une liste des points similaires entre le portlet et le servlet :

- les servlets et les portlets sont des composants basés sur le langage Java pour leur implémentation ;

- les portlets comme les servlets évoluent au sein d'un conteneur ;

- ces deux composants génèrent du contenu (statique ou dynamique) ;

- ils ont tous les deux un cycle de vie contrôlé par leur conteneur et de la même façon ;

- la sémantique concernant les objets resquet et response est identique.

II-B - 2.4. Les points de divergences

Voici une liste des points de divergences entre le portlet et le servlet :

- un servlet génère une page complète tandis que le portlet a pour vocation de ne générer qu'un fragment de page ;

- un portlet peut générer du code HTML sans inclure, de manière rigoureuse, les tags : base, body, frame, frameset, head, html ou title. Le tag iframe peut-être utilisé, mais avec précaution ;

- à la différence d'un servlet, un portlet ne peut être invoqué directement via un URL ;

- la communication entre le client et le portlet est entièrement gérée par le portail ;

- le portlet permet de gérer un état et un mode d'affichage (notion décrite plus bas) ;

- plusieurs instances d'un portlet peuvent être placées dans un même page ;

- deux scopes sont supportés dans l'objet de session : le scope portlet application et le scope portlet ;

- le portlet ne peut pas initialiser l'encodage de caractères de la réponse faite au client ;

- le portlet ne peut pas écrire d'information dans le header de l'entête HTTP sur la réponse faite au client.

Ces listes ne sont pas forcément exhaustives, elles donnent un aperçu des règles à avoir à l'esprit lors du développement de portlet.

III - Description d'un portlet

III-A - Arborescence des fichiers

L'arborescence des fichiers composant le portlet est similaire à celle d'une application web J2EE. La différence réside dans l'ajout d'un nouveau fichier XML : portlet.xml. Ce fichier décrit – de manière déclarative – les composants du portlet.

III-B - Le fichier portlet.xml

Le fichier portlet.xml représente le descripteur de/des portlet(s) contenus dans l'application. Dans la version 1.0 de la spécification des portlet il y a une distinction entre le descripteur de l'application web (web.xml) et celui des portlets (portlet.xml). Cette distinction est due au fait que la version 2.3 de la spécification des servlets définissait le fichier web.xml comme non extensible.

Ci-dessous vous trouvez une représentation graphique des balises et attributs composant le fichier portlet.xml.

Description des balises et attributs du fichier portlet.xml

partie 1

partie 2

IV - Le cycle de vie d'un portlet

Le conteneur fait l'interface entre le portail (l'IHM) et les portlets, il se charge de réceptionner les requêtes issues du client pour les transmettre au portlet concerné. Le cycle de vie d'un portlet peut-être assimilé à celui d'une servlet. Il se réalise au travers de l'invocation de différentes méthodes dans un ordre déterminé. À chaque méthode incombe une responsabilité bien définie. Les paragraphes suivants décrivent différentes phases du cycle de vie d'un portlet.

IV-A - Phase d'initialisation

Cette phase se charge de lire et de mettre à disposition les paramètres déclarés dans le fichier XML de déploiement du portlet.

IV-B - Diagramme de séquence

Le client (via un navigateur web) envoie une requête HTTP vers le serveur de portlet.

Le portail reçoit cette requête. Le conteneur détermine le destinataire de la requête (quel portlet ?).

Le conteneur invoque la méthode ProcessAction() du portlet concerné.

Ensuite le portail va invoquer les méthodes render() de chaque portlet présente sur la page du portlet sollicité par le client.

Les fragments de code HTML seront générés à l'issue de chaque méthode render(). Ces bouts de page vont être agrégés, par le conteneur, pour renvoyer une page au format HTML correctement formatée.

Ci-dessous la représentation au moyen d'un diagramme de séquence :

V - Les méthodes

Ces quatre méthodes sont définies dans l'interface : javax.portlet.portlet Tous les portlets doivent implémenter cette interface directement ou alors, plus communément, par héritage au travers d'une classe l'implémentant (cette façon de faire est généralement utilisée dans le cas de la réalisation de framework autour des portlets). L'API des portlets fournit une implémentation par défaut de cette interface par l'intermédiaire de la classe javax.portlet.Genericportlet.

V-A - Init (portletConfig portletConfig)

Le conteneur invoque une seule fois cette méthode. Cet appel est réalisé lors de la création d'une instance du portlet. L'objet javax.portlet.portletConfig fournit à la méthode d'initialisation certains paramètres décrits dans le fichier portlet.xml.

V-B - Render (RenderRequest rRequest, RenderResponse rResponse)

Cette méthode a pour responsabilité de générer le fragment de code HTML à partir des informations obtenues précédemment.

V-C - Destroy()

Lorsque le portlet est retiré du portail, le conteneur invoque cette méthode afin de libérer les ressources occupées par le portlet.

VI - Mode et état d'un portlet

VI-A - Mode

Un portlet peut s'afficher de plusieurs manières différentes, c'est-à-dire en édition, en visualisation, en mode Aide.

Les modes énumérés précédemment sont les modes standards définis dans la spécification des portlets.

Une implémentation par défaut est définie par la classe javax.portlet.Genericportlet.

Le comportement standard de chaque mode peut-être redéfini par la surcharge de chaque méthode.

VI-A-1 - VIEW

Nom de la méthode : doView().

Ce mode est le standard d'affichage du portlet.

VI-A-2 - EDIT

Nom de la méthode : doEdit().

Ce mode permet de configurer le portlet.

VI-A-3 - HELP

Nom de la méthode : doHelp().

Ce mode permet d'afficher l'aide concernant le portlet courant.

VI-B - États

Le portlet peut prendre plusieurs états de la même façon qu'une fenêtre.

VI-B-1 - CLOSE

Nom de la méthode : allowClose().

Cette méthode est consultée par le portlet manager pour savoir si l'on peut autoriser la fermeture de la portlet.

VII - Informations diverses

VII-A - Les acteurs

Les portlets sont des composants Java s'intégrant dans un portail. Ces composants sont issus d'une spécification : JSR168.

Rédigée par un ensemble d'acteurs du marché, en voici la liste :

- Apache Software Foundation ;

- Bœing ;

- Citrix Systems ;

- IBM ;

- SAP AG ;

- TIBCO Software Inc ;

- Art Technology Group Inc.(ATG) ;

- Borland Software Corporation ;

- EDS ;

- Novell, Inc ;

- SAS Institute Inc ;

- Vignette ;

- BEA Systems ;

- Broadvision Inc ;

- Fujitsu Limited ;

- Oracle ;

- Sybase.

Informations issues du site : Java Community Process.

VII-B - Les API

Actuellement, il existe plusieurs implémentations de la spécification JSR 168 :

- Jakarta JetSpeed 1.3 home page ;

- BEA : Web Logic Portal 4.0 home page ;

- IBM : WebSphere Portal 6 home page ;

- iPlanet : iPlanet Portal Server 3.0 ;

- Oracle : Oracle 9i Portal ;

- SAP Portal ;

- Epicentric portal.

Certaines API (Jakarta Jetspeep, IBM, BEA) sont plus populaires !

VIII - Tutoriel

VIII-A - Prérequis

Ce tutoriel a pour but de montrer les différentes étapes pour implémenter et déployer un portlet.

Nous aurons besoin, pour mettre en œuvre ce tutoriel, d'installer JBossPortal, ainsi que Netbeans 5.5 enrichi d'un plug-in dédié au développement des portlets. Nous verrons l'installation de chacun des produits.

Je considère que vous avez un jdk1.4 minimum installé et correctement paramétré.

VIII-B - Installation de JBossPortal

VIII-B-1 - Téléchargement

Il faut télécharger l'archive contenant le server ici.

Sur la page, il faut sélectionner la ligne suivante :

Copier dans un répertoire nommé jbossPortal (par exemple) l'archive et décompresser là au même endroit.

JBossPortal : Documentation en ligne.

VIII-B-2 - Démarrage et arrêt du serveur

À cette étape, vous devez avoir un répertoire nommé jbossPortal contenant un sous-répertoire nommé jboss-portal-2.4.1.

Pour démarrer le serveur, il faut ouvrir une console (ou un shell) selon votre environnement.

Placez-vous dans le répertoire bin :

Vous pouvez maintenant lancer la commande suivante pour démarrer le serveur :

Selon la puissance de la machine, le démarrage du serveur peut prendre plus ou moins de temps.

Lorsque le démarrage est terminé, vous devriez voir cette ligne dans la console :

Pour arrêter le serveur, il suffit de se placer dans la console où le portail a été lancé et d'utiliser la séquence de touche CTRL + C.

Une fois le serveur arrêté, le système vous rend la main.

VIII-B-3 - Vérification de l'installation

Pour vérifier que le serveur est correctement installé et a bien démarré, tapez dans votre navigateur préféré, l'URL suivante :

http://localhost:8080/portal

Après avoir validé, cette page devrait s'afficher dans votre navigateur :

VIII-C - Installation de NetBeans

VIII-C-1 - Téléchargement

Il faut télécharger le fichier d'installation de la version 5.5 ici.

Choisir le fichier d'installation selon l'environnement de votre machine.

Une fois l'environnement installé, il faut ajouter le plugin permettant la création de portlet.

VIII-C-2 - Installation du plugin

Pour faciliter le développement de portlet, nous allons utiliser un plugin.

Il est téléchargeable ici.

Une fois l'archive du plugin téléchargé, extraire le contenu dans un répertoire temporaire.
Vous devriez trouver trois fichiers :

Nous allons maintenant installer le plugin dans l'IDE. Pour ce faire, il faut démarrer NetBeans. Une fois démarrée, sélectionnez le menu Tools/Module Manager :

Cet écran permet de gérer l'ensemble des plugins installés.

Sur cet écran, cliquez sur le bouton Update.

L'écran suivant apparaît :

Sur celui-ci, sélectionnez le radio bouton suivant :

Ensuite, cliquez sur le bouton next.

Sur cet écran, cliquez sur le bouton Add.

Dans l'écran qui s'affiche, recherchez le répertoire temporaire où le plugin a été dézippé et sélectionnez les trois fichiers portant l'extension *.nbm/

Et validez par le bouton OK.

Vous devriez obtenir l'écran suivant :

Cliquez deux fois sur le bouton next jusqu'à arriver sur l'écran suivant :

Sélectionnez les deux occurrences : Généric portlets et OpenSource PC :

Et enfin, sélectionnez le bouton finish pour terminer l'installation du plugin.

La ligne suivante devrait normalement apparaître dans le module manager :

Cliquer sur le bouton Close pour fermer l'écran du module manager.

VIII-D - Création du portlet : HelloWorldportlet

VIII-D-1 - Création du projet : HelloWorldProject

Pour créer un projet de portlet, il faut sélectionner dans le menu file l'item new Project.

La fenêtre suivante apparaît :

Sélectionner dans la fenêtre de gauche la ligne portlet applications, ensuite dans la fenêtre de droite sélectionner JSR-168 portlet Application.

Voir ci-dessous :

Cliquer sur le bouton next.

L'écran suivant apparaît :

Dans le champ Project Name saisissez 'HelloWorldProject'.

Les autres champs n'ont pas besoin d'être modifiés.

Vous pouvez lancer la création du projet en cliquant sur le bouton finish. Une fois le traitement terminé, le projet suivant devrait apparaître sur la gauche de l'écran :

Cette arborescence de projet contient six répertoires :

- Web pages : contient les jsp correspondant aux différentes vues du portlet ;

- Configuration files : contient un pointeur sur les fichiers de configuration du portlet ;

- Server Resources : contient les ressources externes utiles au portlet ;

- Sources Packages : contient l'ensemble des classes Java composant le portlet ;

- Libraries : contient les différentes bibliothèques du framework portlet et autres bibliothèques nécessaires au fonctionnement du portlet ;

- Tests Libraries : contient la bibliothèque Junit permettant d'implémenter les tests à réaliser sur le portlet.

Vous pourrez parcourir l'arborescence et retrouver les fichiers vus dans la première partie du document.

Création de l'archive de déploiement : HelloWorldProject.war.

Pour créer le l'archive, le plugin met à disposition un script ANT permettant d'automatiser différentes tâches sur le portlet.

Voici la démarche à suivre pour exécuter la tâche de déploiement.

Il faut sélectionner l'onglet Files :

En sélectionnant cet onglet, on peut voir le fichier build.xml.

Sélectionnez le fichier, recherchez dans la fenêtre en dessous la tâche dist.

Faites un clic droit sur la balise, et sélectionnez, dans le menu contextuel, l'item Run target :

L'exécution de la tâche doit générer la trace suivante :

Maintenant l'archive web est générée. Elle est disponible dans le répertoire dist de l'arborescence du projet.

Voyons dans la section suivante comment déployer le portlet sur le serveur JBOSS Portal.

VIII-E - Déploiement et affichage du portlet

VIII-E-1 - Déploiement du portlet

Le déploiement du portlet peut se faire à chaud.

Il faut copier l'archive web générée précédemment dans le répertoire :

Jboss-portal-2.4.1/server/default/deploy.

Une fois le fichier copié, vous devriez voir cette ligne s'afficher dans la console du serveur :

La portlet est maintenant déployée sur le serveur.

Nous allons voir dans la section suivante comment paramétrer le portail pour l'afficher dans une page.

VIII-F - Paramétrage du portail

Dans cette section, nous verrons de manière pragmatique comment paramétrer le portail pour afficher le portlet HelloWorldportlet. Je ne rentrerai pas dans les détails sur les fonctionnalités et les possibilités de paramétrage de Jboss-Portal.

Ceci étant dit, place à l'action…

VIII-F-1 - Création d'une page

Sur la page d'accueil, cliquez sur le lien Admin, il se trouve dans la partie en bas à gauche de l'écran.

Vous devrez vous identifier. Les identifiants par défaut sont : admin - admin.

À l'écran vous pouvez voir plusieurs portlets. Nous allons nous concentrer sur le portlet ci-dessous.

Pour vérifier que le portlet a été déployé correctement, sélectionnez le lien instance puis allez à la fin de la liste.

Vous devriez voir sur la dernière ligne le portlet HelloWorld.

Nous allons créer maintenant une page, elle nous permettra d'afficher notre portlet.

Pour ce faire, cliquez sur le lien portal puis déroulez l'arborescence de la manière suivante :

Ensuite, cliquez sur la page pour obtenir l'écran suivant :

Dans le champ New Page Name, saisissez le nom de la page : HelloWorldPage.

Et validez la saisie en cliquant sur le bouton AddPage.

Voilà l'écran que vous devriez obtenir :

Cliquez sur le nom de la nouvelle page.

VIII-F-2 - Ajout de portlets

Nous allons compléter cette page par des portlets.

Nous allons ajouter dans un premier temps le portlet de navigation. Il permettra de naviguer facilement sur la page d'administration.

Dans la liste déroulante, sélectionnez l'instance nommée NavigationportletInstance et donnez le nom navigation à cette instance.

Une fois l'écran suivant obtenu, cliquez sur le bouton Add navigation :

Le portlet devrait apparaître dans l'arborescence des pages comme fils de la page que nous avons créée.

Sélectionnez l'instance dans l'arborescence.

Cliquez sur le lien thème, vous devriez obtenir cet écran :

Modifiez les listes déroulantes pour obtenir cet écran :

Validez par le bouton Update.

En cliquant sur l'onglet HelloWorldPage, vous devriez obtenir cet écran :

De la même manière que nous avons créé le portlet Navigation.

Nous allons ajouter le portlet HelloWorldportlet.

Nous allons ajouter dans un premier temps le portlet de navigation. Il permettra de naviguer facilement sur la page d'administration.

Dans la liste déroulante, sélectionnez l'instance nommée HelloWorld et donnez le nom MyHelloWorldportlet à cette instance.

Une fois l'écran suivant obtenu, cliquez sur le bouton Add Center.

Le portlet devrait apparaître dans l'arborescence des pages comme fils de la page que nous avons créée.

Vous pouvez maintenant cliquer sur le lien HelloWorldPage.

Vous devriez obtenir l'écran suivant :

IX - Conclusion

Nous avons vu dans ce tutoriel comment créer et déployer un portlet basic.

À partir de cet exemple, vous pourrez faire évoluer ce portlet pour l'enrichir et mieux comprendre les mécanismes.

Si vous avez des questions vous pouvez me contacter, ou alors poser vos questions sur le Forum développement Web en Java.

X - Remerciements

Merci à ChristopheJ, zekey et Ricky81 qui ont eu la patience de relire et de commenter cet article.