darkBlog

lundi 15 octobre 2007

Déploiement de portlets JSR 168 et représentation interne dans WebSphere Portal

Déjà évoqué dans le second billet traitant du développement de portlets avec Jetspeed et Eclipse, les informations que l'on retrouve dans WebSphere Portal à l'issue du déploiement d'un portlet JSR 168 proviennent du descripteur de déploiement portlet.xml dudit portlet. Cela dit, comme ce fichier peut se montrer plutôt verbeux, et que sa représentation XMLAccess l'est encore davantage, difficile de déterminer le rôle et l'impact précis de chacune des données du descripteur de déploiement.

C'est pourquoi je me suis livré à une petite expérience visant précisément à lever le voile sur cette zone d'ombre. En ressort que peu d'informations sont réellement utilisées, mais qu'elles sont essentielles et qu'il convient de les manipuler avec précaution (j'y reviendrai plus loin). Voici deux extraits de ces fichiers, volontairement épurés :

Descripteur de déploiement du portlet :

<portlet-app id="FOO">
    <portlet>
        <portlet-name>BAR</portlet-name>
        <portlet-info>
            <title>PLOP</title>
        </portlet-info>
    </portlet>
</portlet-app>

Puis l'export XMLAccess du portlet :

<web-app uid="FOO.webmod">
    <servlet referenceid="BAR.servlet">
    <portlet-app name="FOO" uid="FOO">
        <localedata locale="fr">
            <title>FOO</title>
        </localedata>
        <portlet name="BAR">
            <localedata locale="fr">
                <title>PLOP</title>
            </localedata>
        </portlet>
    </portlet-app>
</web-app>

Il apparaît que les deux données majeures sont la balise portlet-name ainsi que l'attribut id de la balise portlet-app : à elles seules, elles déterminent les données vitales du portlet déployé dans WPS.

Pourquoi tout ceci est important et que je vous bassine avec ? Parce qu'une mauvaise manipulation, même motivée par de très bonnes intentions, peut avoir des conséquences dramatiques. Un exemple ? Imaginez que pour une quelconque histoire de suivi de conventions de nommage (ce qui est tout à votre honneur), vous décidiez de modifier la balise portlet-name du descripteur de déploiement. Redéployez votre module web, et vous perdez tous les portlets issus du module dans votre portail1.

Bug de WPS ? Non, en réalité, la modification du portlet-name a entrainé des modifications de la servlet sous-jascente ; en effet celle-ci se voit attribuée un nouveau referenceid (celui-ci étant basé sur la valeur du portlet-name), et du coup, d'un nouvel objectid, WPS devant considérer que la servlet a changé (et ça semble compréhensible, le referenceid étant le seul attribut utilisé pour l'opération de lookup). Et vos portlets existants, liés à cette servlet par l'attribut servletref, disparaissent soudainement de la surface de votre portail. Oui, c'est sournois, mais ça peut arriver, et très facilement. Les exports XMLAccess sont formels.

Que retenir de tout ceci ? Que le portlet-name comme l'attribut id de la balise portlet-app sont les données les plus importantes du descripteur de déploiement, et qu'une fois un module déployé, mieux vaut ne jamais toucher à ces valeurs.

1 : c'est du vécu. Et ce comportement est reproductible avec WPS 5.1 et 6

jeudi 2 août 2007

Exécuter des scripts XMLAccess via HTTP

Les deux méthodes classiques d'exécution de scripts XMLAccess sont d'une part l'importation depuis l'interface d'administration du portail (Paramètres du portail > Importation XML), d'autre part l'outil en ligne de commande xmlaccess.sh (ou .bat) que l'on lance directement depuis le serveur. Mais il en existe une troisième, vraissemblablement moins connue - en tout cas non mentionnée dans l'infocenter - qui consister à communiquer avec le serveur directement via le protocole HTTP.

Le principe est simple :

  • Une requête HTTP de type POST est effectuée sur /wps/config (ex : http://wps.ftel.lan:9081/wps/config)
  • Les accréditations de l'administrateur sont transmises via les entêtes HTTP WPS-User et WPS-Password (pour les versions de WPS plus anciennes, l'unique entête WPS-Authorization, concaténation du login et du mot de passe séparés par un ':', était de vigueur. Le plus simple est de mettre les deux.).
  • Le script XMLAccess à proprement parler est transmis en tant que contenu "brut" de la requête.

En guise de réponse, le portail retourne une page HTML dont le contenu est le résultat de l'exécution du script XMLAccess. Petite démonstration.

Tout d'abord, la requête HTTP :

http://wps.ftel.lan:9081/wps/config

POST /wps/config HTTP/1.1
Host: wps.ftel.lan:9081
WPS-User: wpsadmin
WPS-Password: mypassword
WPS-Authorization: wpsadmin:mypassword
Content-Type: text/xml
<?xml version="1.0" encoding="UTF-8"?>
<request
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="PortalConfig_1.3.xsd"
type="export">
  <portal action="locate">
  <skin uniquename="ftel.skins.BlackSkin" action="export"/>
</portal>
</request>

A titre purement informatif, la réponse du portail :

HTTP/1.x 200 OK
Server: WebSphere Application Server/5.1
Content-Type: text/html; charset=ISO-8859-1
Content-Language: en
Transfer-Encoding: chunked

Nettement plus intéressant, le résultat de l'exécution du script XMLAccess :

<?xml version="1.0" encoding="UTF-8"?>
<request xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" build="wp5102_032" type="update" version="5.1.0.2" xsi:noNamespaceSchemaLocation="PortalConfig_1.3.1.xsd">
  <portal action="locate">
    <skin action="update" active="true" default="false" objectid="_K_002C1DBG030CI830_IP" resourceroot="BlackSkin" type="default" uniquename="ftel.skins.BlackSkin">
      <localedata locale="fr"><title>FTEL : Black Skin</title></localedata>
    </skin>
  </portal>
  <status element="all" result="ok"/>
</request>

Et voilà ! Quel intérêt me diriez-vous ? Et bien ceci rend possible l'exécution de scripts XMLAccess à distance (ce qui reste possible avec l'outil xmlaccess.sh sous réserve de l'avoir installé), mais aussi - plus intéressant - par programmation. Une des premières applications qui me vienne à l'esprit est de combler les manques et/ou palier aux lourdeurs de l'interface d'administration par de petits scripts PHP, par exemple pour faire du nettoyage (suppression des portlets applications qui n'ont plus de portlets), ou encore effectuer rapidement des tâches coûteuses en clicks (changer toutes les langues d'une page ou d'un portlet). C'est d'ailleurs ce que nous sommes en train de faire chez mon client, et c'est très prometteur.

Pour ceux qui se demanderaient pourquoi PHP, ce choix s'impose de lui même : PHP possède une extension à la fois simple et très puissante de traitement de données XML (SimpleXML), et le Zend Framework propose un client HTTP bien commode (Zend_Http_Client). Ces deux éléments réunis, exécuter scripts XMLAccess puis en analyser les résultats en PHP est un jeu d'enfant.

Pour la route et en guise de conclusion, voici un exemple d'export complet d'un portail avec Zend_Http_Client :

$script = "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n
  <request xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\" xsi:noNamespaceSchemaLocation=\"PortalConfig_1.3.xsd\" type=\"export\">\n
    <portal action=\"export\"/>\n
  </request>";

$client = new Zend_Http_Client("http://wps.ftel.lan:9081/wps/config");

$client->setHeaders(array(
  'WPS-User' => $username,
  'WPS-Password' => $password,
  'WPS-Authorization' => $username . ":" . $password
));
$client->setRawData($script, 'text/xml');
$client->setMethod(Zend_Http_Client::POST);

$response = $client->request();

$result = $response->getBody();

mardi 3 juillet 2007

Imports XMLAccess et nouveaux skins

Lorsqu'on réalise un import XMLAccess1 qui contient de nouveaux skins2 dans WebSphere Portal 5.1(.0.2), selon toute vraissemblance ceux-ci ne sont pas disponibles de suite. Ce qui est très perturbant car tout le reste de ce qui a pu être importé l'est instantanément (thèmes, modules web, portlets, instances de portlets, pages, mappings d'URL, etc). Les skins sont bien listés dans l'interface d'administration, mais on ne peut pas les affecter aux instances de portlets (retour au skin par défaut). Et c'est d'autant plus perturbant qu'un skin aux paramètres identiques installé à la main (et donc utilisant les mêmes ressources JSP, CSS, etc) depuis l'interface d'administration suscitée marche quant à lui du premier coup.

Donc pas la peine perdre passer l'après-midi à triturer dans tous les sens les 3000 lignes du script d'import, suffit d'attendre un peu (enfin, beaucoup), ou de redémarrer le portail (ce qui peut être très long aussi, notez), et le tour est joué. Sans doute une sombre histoire de cache dont je ne préfère pas vraiment en savoir plus.

1 : j'en ai déjà un peu parlé ici. XMLAccess est un dialecte XML qui décrit l'ensemble de la configuration d'un portail WebSphere ; ce qu'est DXL à Domino, en somme.

2 : un skin est l'habillage d'un portlet. C'est le fragment qui contient le cadre, le titre du portlet, les actions (configurer, éditer, minimiser, maximiser), etc.

samedi 5 mai 2007

Développement de portlets pour WebSphere Portal avec Jetspeed et Eclipse (2/2)

Ce billet fait suite à Développement de portlets pour WebSphere Portal avec Jetspeed et Eclipse (1/2), dont je vous conseille grandement la lecture si vous souhaitez comprendre ce qui va suivre. Sont ici abordés quelques aspects de la spécification JSR-168, le développement puis le déploiement du portlet dans Jetspeed et WebSphere Portal.

Read next

mardi 1 mai 2007

Développement de portlets pour WebSphere Portal avec Jetspeed et Eclipse (1/2)

Pour développer des portlets pour WebSphere Portal, IBM propose toute une gamme de logiciels s'adressant à des publics, des besoins, et des budgets différents, tels que Rational Application Developer, l'environnement de développement étendu à destination des développeurs Java chevronnés, Lotus Component Designer s'adressant à la population des développeurs Lotus/Domino et qui a été évoqué récemment ici-même, ou encore WebSphere Portlet Factory qui permet le développement et le déploiement accéléré et grandement automatisé de portlets à l'aide d'assistants visuels et d'un grand nombre de connecteurs vers les systèmes d'entreprise (Domino, SAP, etc).

Mais les portlets répondent désormais à un standard (actuellement la spécification JSR-168 ou Portlet-1.0, la relève JSR-286, Portlet-2.0, étant toujours à l'état de brouillon), standard supporté par WebSphere Portal depuis la version 5.02. Et pour des besoins modestes - ou même complexes, du moment qu'ils ne fassent pas intervenir des spécificités de WPS comme les thèmes, le modèle de navigation ou encore la sécurité (cf le modèle SPI) - il est tout à fait possible de développer des portlets intégralement à l'aide de logiciels open-source comme Apache Jetspeed, le portail d'entreprise de la fondation Apache, et Eclipse, le couteau suisse communautaire qui reste au demeurant un excellent environnement intégré de développement. Bien sûr, ils n'adressent pas les mêmes problématiques, mais outre leur gratuité, ils ont l'avantage d'être légers et rapides, et pour le développeur Java, ceux-ci se posent en sérieuse alternative au mastodonte RAD et ses environnements de test (UTE) aussi pratiques que gourmands en mémoire. C'est ce que je vais vous présenter dans ce billet en deux parties1, de l'installation de ces outils jusqu'à la publication d'un portlet dans WPS 6.

1 : La deuxième partie est presque terminée et sera publiée dans la semaine, histoire d'éviter la blague des suites 3 mois après.

Read next

mardi 20 mars 2007

Dojo Toolkit ou Prototype ? Les deux mon capitaine !

Ce titre est quelque peu érroné puisque contrairement à la croyance populaire (ou la mienne, du moins), le thème par défaut de Websphere Portal 6.0 ou encore les fonctionnalités de drag 'n drop des thèmes ne sont pas réalisés avec le Dojo Toolkit, mais vraissemblablement avec du code maison (et au passage, il y a l'air d'en avoir un bon paquet). Quoi qu'il en soit, pour peu que vous ayez suivi les récents événements, vous conviendrez qu'il apparaît incontestable qu'IBM adopte en force le toolkit Dojo pour ses interfaces riches.

Ce soir, je me suis essayé à Lotus Component Designer 6.0 - le "nouveau"1 produit qui s'adresse à la population des développeurs Notes et Domino pour mettre au point des portlets - et j'avoue avoir été franchement surpris de constater que le code Javascript généré par ce dernier est basé sur Prototype et script.aculo.us. La version 1.5.0_rc0 pour être précis (oui, une première release candidate, même pas peur !).

Lotus Component Designer : exemple de contrôles avec prototype et script.aculo.us
Eh oui, Lotus Component Designer génère automatiquement
des contrôles avancés, comme des calendriers, ou de l'autocomplete.
Le genre de choses dont tout développeur Domino rêve,
mais n'aura vraissemblablement jamais (ou pas tout de suite
(mais en fait je sais pas plus que vous)).

Le revers de tout ceci, c'est qu'au final, il y a 2 frameworks javascript chargés dans la page. Ceux-ci ne semblent pas tomber en conflit, et tant mieux (rappelez vous mes problèmes avec Prototype et JSval rapidement évoqués dans le lien précédent), mais le temps de chargement s'en fait clairement ressentir. Afficher le portlet de la capture d'écran en mode édition ? Sans cache, 14.01 secondes pour 51 requêtes HTTP et un total de 1.25 Mo me dit Firebug. Oui, ça commence à faire beaucoup.

Nous migrons très prochainement de WPS 5.1 à 6.0. Je sens que je vais m'amuser à intégrer tous les portlets réalisés à base de YUI... Quoi qu'il en soit, je trouve cette découverte surprenante. Et vous, ça vous inspire quoi ? (Et hop, une conclusion à la Fred Cavazza, une).

1 : du moins nouvellement renommé, puisqu'il s'agit manifestement en grande partie de feu Workplace Designer

PS : ce billet a été intégralement rédigé à l'aide de jus de tomate. Aucun citron-vert n'a été blessé.

vendredi 9 mars 2007

Développement WebSphere Portal : par où commencer ?

Vous l'avez probablement constaté, en ce moment, les portails ont le vent en poupe. Ca tombe bien, depuis quelques temps, je suis plutôt versé sur WebSphere Portal, et ce n'est pas pour me déplaire après 3 ans & demi consacrés quasi-exclusivement au développement Lotus Domino (avec un peu de PHP entre les deux). Toutefois, c'est un univers vaste et très différent de ce dernier, et la bête n'est pas forcément facile à dompter ni même à aborder. Voici quelques liens que j'ai recueilli au fil de mes aventures et qui pourraient intéresser ceux qui débutent dans le domaine :

C'est tout pour le moment, je compléterai probablement cette liste au fur & à mesure de mes découvertes. De manière générale, votre premier réflexe doit être de consulter l'Info Center (v5.1, v6.0) car celui-ci est très complet et regorge de tas d'infos indispensables.

samedi 3 mars 2007

Deux conseils pour installer correctement WebSphere Portal Express 6.0 sous Windows

  • Optez pour un chemin d'installation succint (ex: C:\PE au lieu du C:\Program Files\IBM\PE proposé à l'installation), choisissez des noms de cell et de node les plus courts possibles, sous peine de rencontrer des erreurs de ce type (WebSphere Portal comporte des noms de fichiers et des arborescences à rallonge qui peuvent mal passer sous Windows).
  • Si votre installation plante sur le disque W-III et que l'erreur mentionnée ci-dessous apparaît, renommez le fichier com.ibm.wsspi.(...).portscommandsmsg.xml comme indiqué dans le message d'erreur (il lui manque un 's' à la fin) et relancez l'installation (et vous aurez alors perdu une 20aine de minutes).
(2 mars 2007 20:55:50), Install, com.ibm.ws.install.ni.ifactory.ismp.actions.InstallMaintenancePackage, err, java.io.IOException: C:\i\2\windows\ia32\ifpackage\WAS\repository\admin.ports\properties\messages\en\com.ibm.wsspi.management.commands.resources.portscommandsmsgs.xml (The system cannot find the file specified)
(2 mars 2007 20:55:59), Install, com.ibm.ws.install.ni.ifactory.ismp.actions.ISMPLogSuccessMessageAction, msg1, INSTCONFFAILED

jeudi 19 octobre 2006

IE7 et Websphere Portal 5.1 sont dans un bateau. Qui tombe à l'eau ? Les iframes !

A moins de ne pas avoir allumé votre ordinateur de la journée, il y a assez peu de chances pour que vous soyez passé à coté de la sortie d'IE7. Cet après-midi, je l'ai installé dans une machine virtuelle afin de tester la compatibilité des applications web de mon client. En allant voir le portail de l'entreprise basé sur IBM Websphere Portal 5.1, j'ai été très surpris de tomber sur le message suivant :

The portlet cannot be displayed because your browser does not support iframes
Un portlet de clipping avec IE7

J'ai d'abord cru à une blague de Microsoft, du genre désactivation des iframes dans la configuration par défaut pour une vaseuse excuse de sécurité (ils l'ont bien fait du jour au lendemain pour les identifiants dans l'URL1, hein). Après un petit tour infructueux du coté des options d'IE7, je suis finalement allé jeter un coup d'oeil à la configuration du portail. Et c'était bien là que la solution résidait.

En effet, il s'avère que WPS rend les pages différemments selon les capacités des agents utilisateurs, et que forcément, IE7 n'étant pas déclaré dedans, c'est le mode le plus dégradé qui a été proposé. Une louable intention, mais qui nous a fait une belle frayeur quand même (surtout à mon client, qui s'est décomposé à une vitesse que je n'aurais pas cru biologiquement possible). Bref, une petite modification de la regexp de détection des agents utilisateur et le problème était réglé.

Ecran de configuration des agents utilisateur
Avec une règle prioritaire on matche désormais toutes
les versions d'IE. Comme ça on est prêt pour IE 8.

1 : Ce qui empêche au passage d'utiliser le credential vault du portail pour l'authentification BASIC et nous oblige à implémenter tout un tas de bidouilles pour fournir un service équivalent. Vous n'avez pas idée de l'énergie inutilement déployée comme de l'argent gaspillé à cause de cette "mise à jour de sécurité".