Archive for the ‘JEE5’ Category

Maven et gestion des dépendances

novembre 22, 2009

Une fonctionnalité de Maven est la gestion des dépendances. Sur ce point, Apache Ant sont « concurrent » ou plutôt son alternative n’offre pas d’équivalent. Il faut alors se tourner vers Apache Ivy pour avoir quelque chose d’équivalent, en fait quelque chose de mieux.

Mais même avec Maven, la gestion des dépendances peut devenir complexe. Ce problème de dépendance trouve certainement son origine dans le format des fichiers Jar. Une amélioration de ce format est prévu dans la version 7 du langage java. Il s’agit de JAM ou Java Module. Mais comme je travaille encore avec la version 5 de Java, il est fort probable que je vais continuer à rencontrer des problème sur les dépendances.

Dans un exemple récent, j’ai repris un ancien projet basé sur Xfire pour développer un service Web. Xfire n’est plus maintenu. Sa dernière version la 1.6 date de mai 2007. Je ne vous conseille donc pas l’utilisation de ce framework mais de passer à CFX.

Le projet initial n’était pas sous Maven. J’ai donc ajouter dans mon projet Eclipse dans le nouveau fichier pom, la dépendance suivante:


<dependency>
<groupId>org.codehaus.xfire</groupId>
<artifactId>xfire-all</artifactId>
<version>1.2.6</version>
</dependency>

Ceci provoque l’ajout de 48 jar au niveau du Maven Dependancies du projet. Cette liste de dépendance n’est plus pas triée par ordre alphabétique. C’est sans doute le petit élément qui peut m’agacer le plus. Un petit survol montre que la liste de jars contient junit et jmock qui sont à priori inutile. Ceci vient sans doute également qu’Eclipse ignore la notion de scope au niveau des dépendances. Ainsi Junit devrait avoir le scope « test » pour indiquer qu’il est utilisé lors de la compilation et l’exécution des tests, pas lors de la compilation du code source.

Un plugin Maven « dependency » permet d’y voir un peu plus clair. La commande mvn depency:tree affiche les dépendances sous un forme arborescente et mvn dependency:copy-dependencies va copier l’ensemble des dépendances et les mettre dans le dossier target\depencies. Il est possible ensuite d’utiliser la commande exclude au niveau des dépendances maven pour faire un peu le trie.

Publicités

Rapprochement entre WebDriver et Selenium

octobre 31, 2009

Webdriver et Seleniumhq sont des outils de tests des applications web. Au départ webdriver est projet hébergé dans Google code.

Depuis le septembre, les deux projets se sont rapprochés et les jars les plus récents de WebDriver sont maintenant disponibles sur le site « Open QA ». Selenium RC (Remote Control) permet de piloter des navigateurs Web et l’API peut être utilisée avec de nombreux langages dont Java. WebDriver est une API de haut niveau qui permet soit de piloter des navigateurs soit d’utiliser une API de plus bas niveau HtmlUnit permettant de simuler un navigateur Web. Ce qui permet soit de jouer les test dans un vrai navigateur soit de les jouer sans aucune interface. Ce dernier cas est intéressant dans le cadre d’une intégration continue. Une autre particularité de WebDriver est la volonté de fournir une API simple. Le projet n’est cependant pas encore tout à fait mature, ce qui est compréhensible puisqu’il a commencé en mars 2008.

Pour l’instant pour mes projets, je continue à utiliser JwebUnit qui finalement est assez proche dans ses principes à WebDriver. Mais je pense à l’avenir que WebDriver / Selenium est une alternative valable.

EJB3Unit extension de JUnit pour les applications EJB3/JPA

septembre 27, 2009

Je me suis posé à nouveau le problème des tests unitaires dans le cadre d’applications EJB3/JPA, en fait deux applications. Ces applications contiennent grossièrement trois couches. La couche externe est un ensemble de stateless session beans. La couche intermédiaire sont des « queries », ce sont des stateless session beans simples effectuant des recherches dans la base de donnés. Enfin la dernière couche sont les entités des objet persistants contenant du métier.

La particularité de mes applications est bien que le métier se trouve essentiellement dans les entités et non dans les sessions beans qui eux effectue des tâches essentiellement techniques comme la gestion de la transactions. Attention, JPA est un peu limité par rapport à Hibernate et certains traitements doivent être placés au niveau des session beans.

Autre point important dans l’architecture est de respecter le principe suivant : statefull session beans > stateless session beans > entities. Ce qui signifie qu’un statefull session bean peut appeler des statefull session beans, des stateless session beans et des entités. Un stateless session bean peut appeler des stateless session beans et des entités, mais jamais de statefull session beans. Enfin, une entité ne peut appeler que des entités.

Ce dernier point rend les entités complètement indépendantes de JPA. Il est donc possible de faire les tests unitaires sans se préoccuper de la partie persistance. Ce qui renforce l’impression de framework « transparent » pour JPA.

Tester les queries et les session beans est plus complexe. Pour ces dernier, il faut un conteneur EJB3. J’utilise OpenEJB qui permet d’avoir un conteneur simple à utiliser lors de mes test. Enfin, il faut des donnés de tests. Actuellement, j’utilise des scripts SQL pour initier des donnés de test pour les queries. Enfin pour les session beans, j’utilise des méthodes qui alimentent la base de données. Ce dernier point peut devenir très lourds pour les session beans gérant les entités les plus complexes.

Ce principes d’écriture des tests unitaires fonctionnaient à près bien sans être tout à fait satisfaisant, au moins pour ma première application. En effet la base de données après les tests est polluée par les données de test introduites. Cependant, ceci devient ingérable pour ma seconde application, soit trop complexe, soit mal écrite…

J’ai appris l’existence de EJB3Unit récemment. En fait, cet outil montre quelque chose d’essentiel. Tout comme les servlets et filtres Java, les session beans sont des objets utilisables uniquement dans un conteneur (de servlets pour les servlets et les filtres). Ils nécessite un framework particulier de test. Pour les servlets, il s’agit de Cactus, pour les session beans EJB3 se serait EJB3Unit. Par contre du fait de la transparence de la persistance, EJB3Unit n’a pas d’intérêt pour les entités. J’ai bien mis le conditionnel, car ce projet semble abandonné par ces développeur depuis plus d’un an. Et la dernière version stable est incompatible avec mes applications EJB3.

Utilisation de Maven2 en tant qu’outils de génération de rapports

janvier 1, 2009

Maven2 est un outils fascinant pour les personnes travaillant sur les projets Java. Il permet de gérer en premier les dépendances du projet. Mais il fournit d’autres fonctionnalités comme la génération de rapports (recherche de bugs, suivi de conventions de code, métriques), ceci en ajoutant quelques lignes de déclaration. En fait il prépare l’industrialisation des développements.

Les rapports sont générés suivant le cycle normal de Maven, par la commande : « mvn site:site ». Pour la génération de ces rapports, je conseille fortement d’utiliser Maven en ligne de commande et non le plugin m2 d’Eclipse (pour les utilisateurs de cet IDE). En effet, il existe trop de petits bugs dans ces plugins Maven pour Eclipse. Le rapport par défaut prévoit plusieurs informations de bon sens (about, project license, project team) qu’il est possible de renseigner dans le fichier pom.xml du projet.

Il est possible d’ajouter des plugins pour obtenir des rapport supplémentaires. Ceci se fait dans le noeud « reporting » du fichier pom.xml. Le plugin proviennent essentiellement du projet maven lui-même ou du projet mojo.codehaus.org. La déclaration est très simple en général, il suffit d’indiquer le groupId et l’artifactId du plugin. Les maniaques peuvent ajouter le numéro de version. Cette simplicité contraste avec le travail fait avec Ant.

Les premiers plugins que je propose d’utiliser sont en fait des plugins simples qui ne correspondent pas vraiment à des rapports classiques mais à des outils plus généraux. Le premier jxr (ou Xref) met simplement sous forme HTML le code source et celui des tests unitaires. Ce code source sera utilisé par d’autres plugins pour indiquer explicitement les lignes de code en problème. Ainsi, si un plugin (comme checkstyle) dit que telle ligne de code de telle classe ne respecte pas une convention de code, il est toujours plus agréable d’avoir un lien sur la ligne en question. La déclaration de ce plugin dans la partie reporting est :


<plugin>
   <groupId>org.apache.maven.plugins</groupId>
   <artifactId>maven-jxr-plugin</artifactId>
   <version>2.1</version>
</plugin>

Le second plugin est celui qui génère la javaDocs. Il est vrai que le format de la javaDocs est un peu vieillot mais il est largement utilisé dans les projets Java. Ensuite Eclipse permet de générer cette javaDocs, mais l’avantage de l’automatisation et l’intégration dans les rapports.


<plugin>
   <groupId>org.apache.maven.plugins</groupId>
   <artifactId>maven-javadoc-plugin</artifactId>
   <version>2.5</version>
</plugin>

Le troisième est également un plugin « simple ». Il s’agit de Surefire qui génère un rapport des tests unitaires dans le cadre des frameworks JUnit ou TestNG. L’écriture des tests unitaires est un point important pour un développement de qualité. Il faut cependant admettre qu’avoir le bon niveau de test n’est pas évident. Un détail important Maven ne semble pas exécuter les tests unitaires pour JUnit dans le même ordre que le plugin JUnit pour Eclipse. En soit, c’est une bonne chose, car les tests unitaires doivent être indépendants les uns des autres.


<plugin>
   <groupId>org.apache.maven.plugins</groupId>
   <artifactId>maven-surefire-report-plugin</artifactId>
   <version>2.4.3</version>
</plugin>

Le quatrième plugin que je propose analyse le code, de manière simple. Il s’agit de taglist. Il va repérer les tags //TODO ou @todo laissés dans le code. Il est possible d’ajouter d’autres tags (par exemple @deprecated ou //FIXME) en configurant le plugin. Un conseil en passant, les //TODO sont généralement créés par les générateurs de code. Je ne les efface pas mais je remplace par des //DONE. Dans l’exemple suivant je configure explicitement 4 tags


<plugin>
   <groupId>org.codehaus.mojo</groupId>
   <artifactId>taglist-maven-plugin</artifactId>
   <version>2.3</version>
   <configuration>
      <tags>
         <tag>TODO</tag>
         <tag>FIXME</tag>
         <tag>@todo</tag>
         <tag>@deprecated</tag>
      </tags>
   </configuration>
</plugin>

Il existe d’autres plugins comme checkstyle, cobertura, pmd, JDepend. A vos de les étudier et de voir ce qui convient à votre projet.

L’outil d’automatisation Maven2

novembre 8, 2008

Maven est un outil dont la notoriété et l’utilisation augmente dans le monde Java. Son utilisation croit également dans le cadre de l’entreprise. D’autre part, son utilisation se répand largement dans les projets libres. Il facilite largement la tâche de recompiler un projet libre à partir du code source. Je tenterai ici d’expliquer pourquoi.

Il s’agit notamment d’un outil d’automatisation des tâches, même si ce point de vue est un peu réducteur. Il remplace avantageusement Ant pour la partie automatisation. Dans cette présentation, je me limite à Maven2. En effet, Maven1 était un Ant un peu amélioré sans intérêt réel maintenant.

Maven comme Ant permettent d’automatiser les tâches dans un projet Java, comme la compilation, la génération d’archive, de rapport. Dans Ant, on définit certaines tâches, cela ressemble un peu à de la programmation. C’est donc bien adapté à l’état d’esprit d’un développeur. Mais finalement, on a l’impression redéfinir la roue à chaque fois et les scripts Ant peuvent devenir très longs, peu normalisés et difficiles à comprendre par une personne étrangère à l’équipe projet. Quant à Maven, il se base sur un principe complètement différent de Maven. On ne déclare pas de tâches, elles sont prédéfinies. C’est assez logique. Un projet Java doit être compiler, il devrait être testé, il doit permettre la création d’une archive comme un jar ou un war pour être utilisé facilement par d’autres projets. Donc la commande « mvn test » exécute les tests unitaires, « mvn package » génère l’archive associée au projet, et ceci pour tous les projets utilisant Maven. Il est possible de générer avec Maven, les rapports associés aux outils de qualité comme checkstyle et cobertura.

Comment fonctionne alors ce magique outil Maven ? Le développeur définit dans le fichier pom.xml la structure du projet. Je ne déclare pas les actions à effectuer sur le projet mais comment est structuré le projet. Cette approche déclarative n’est pas forcément la plus proche de l’état d’esprit du développeur mais est ici beaucoup plus efficace. Un autre point diminue fortement la taille du fichier pom.xml, Maven se base sur des conventions. Le code source se trouve par défaut dans le répertoire src/main/java. Il est toujours possible de le placer ailleurs mais finalement il est mieux de suivre les conventions. Le seul cas où il reste utile de surcharger les conventions est lorsqu’on reprend d’anciens projets archivés sous CVS. Le déplacement d’un fichier avec CVS fait perdre l’historique.

Maven gère également les dépendances entre projets avec les versions. Un projet java classique va utiliser le framework de test Junit (version 3 ou 4), la librairie log4j pour la gestion des traces techniques. On déclare explicitement les dépendances et leurs portées (test, compile, runtime). Ceci est sans doute une réponse provisoire au grand désordre qu’est la non gestion des dépendances dans le monde Java (et je suis très poli ici : c’est le vrai B***).

Il demeure cependant quelques problèmes lors de l’utilisation de Maven. Le premier est le manque d’intégration dans Eclipse. Ce problème était important il y a quelques temps. Maintenant, il existe deux plugins m2eclipse et q4e. J’utilise le premier dans mon activité professionnelle, ceci de plus en plus. Le second q4e est un projet Google. Il apparaît plus ambitieux que m2. Il propose notamment une vue graphique des dépendances. Maintenant, l’installation par le site update ne fonctionne pas. Je ne le conseille pas un premier temps et je vous propose m2.

Les plugins ne font pas tout. Il existe un manque dans Eclipse au niveau de la hiérarchie des projets. Tous les projets Eclipse sont au même niveau. Tandis que Maven autorise des hiérarchies de projets. En fait ceci est imposé par Maven du fait qu’un projet Maven correspond à un seul artefact (pas deux ou plusieurs). Ceci risque d’engendrer un nombre important de projets Eclipse. Notons qu’Eclipse n’a pas de notion de portée des dépendances. Donc si vous utiliser Junit, une librairie Junit*.jar apparaît dans la liste des dépendances alors qu’avec Maven on peut indiquer que cette dépendance ne concerne que la partie des tests, et non l’utilisation de l’archive dans un autre projet.

Autre point délicat, je découvre régulièrement des petits bugs dans les plugins Maven de métriques et de qualité du code.

Utilisation de GCJ sous Windows

octobre 6, 2007

GCJ est le projet du compilateur libre GNU pour le langage Java. Il existe deux projets de permettant l’utilisation de GCJ sur Windows MinGW et Cygwin. En fait ce sont les projets de portage du compilateur C C++ GNU GCC. J’ai tenté d’utiliser sans succès GCJ avec MinGW. Je me suis tourné sur Cygwin. Mon objectif est simple ici compiler ce programme Java simpliste qui affiche un message à la console avec GCJ.

public class HelloWorld {
	public static void main(String [] args) {
		System.out.println("Hello");
	}
}

Lors de l’installation de Cygwin, il faut choisir dans les packages « devel » gcc-java et libiconv une librairie indispensable à la compilation des codes java. C’est l’absence de cette librairie qui m’a fait abandonner MinGW

compiler pour générer un exécutable (génère par défaut un fichier a.exe)

gcj --main=HelloWorld HelloWorld.java

Les options sont similaires à celle de gcc. Pour spécifier un nom de fichier, il suffit d’utiliser l’option o. Cet exécutable fonctionne correctement sous Cygwin, mais si vous voulez l’utiliser sous Windows vous devez ajouter 3 dll dans le répertoire system32 de Windows (cygwin1.dll cygiconv-2.dll, cygz.dll).

gcj --main=HelloWorld HelloWorld.java -o HelloWorld.exe

compiler pour générer un fichier class pour classique pour la JVM, il faut utiliser l’option C. Le fichier class obtenu peut être exécuter avec la JVM

gcj -C HelloWorld.java

java -cp . HelloWorld

Maintenant, avec la libéralisation du langage Java, le projet gcj perd de l’intérêt. Cependant, gcj est capable de compiler des projets « lourd » comme Eclipse.

L’outil de test DBUnit

mai 28, 2007

Cet article concerne toujours les tests unitaires et les frameworks de type xUnit. Rappelons que la référence pour le monde java est JUnit. Je sais il manque un article sur JUnit, il viendra un jour.

DBUnit est une solution pour la mise en place de tests unitaires dans le cadre d’application Java mettant en oeuvre des bases de données relationnelles. La version actuelle, la 2.2 date du 27/12/2006. Le site du projet est http://dbunit.sourceforge.net/. Le projet est resté semble-t-il plusieurs mois en sommeil, mais maintenant il est à nouveau actif. Comme d’habitude la documentation n’est pas satisfaisante !

DBUnit fonctionne comme une extension de JUnit. Pour rappel, dans JUnit, il existe deux classes importantes les « TestCase » qui sont les tests unitaires et les « TestSuite » qui regroupent un ensemble de tests (donc des TestCase ou des TestSuite). Le principe de DBUnit est d’étendre la classe TestCase avec la classe DBTestCase. Cette classe comporte les méthodes permettant d’alimenter le contenu des tables de la base de données avec les données que vous désirez. Ces données peuvent être définit dans un fichier XML. Enfin DBUnit vous fournit des assertions supplémentaires permettant de comparer le contenu d’une table avec un contenu attendu défini dans un fichier XML.

Il est possible de faire les tests unitaires uniquement avec JUnit. C’était effectivement la voie que j’avais prise. Mais finalement, une fois que j’ai réussit à faire fonctionner DBUnit, j’ai réellement trouvé l’outil intéressant.

L’outil Jester

mai 20, 2007

Jester est un outils testant la qualité des tests unitaires écrits dans le cadre du framework JUnit. Il teste les tests… Il recherche les parties de codes non couvertes par les tests unitaires. Je suis tombé par hasard sur cet outil durant ma lecture du livre « Test Driven Development » de Kent Beck.

Cet outil se base sur le principe de « Mutation testing » ou « Mutation analysis » qui peut être transcrit en français par « test par mutation ». Le principe est le suivant, on injecte artificiellement des fautes dans un programme (le mutant) et on regarde si les tests sur le programme détecte l’erreur (killed mutant). Le problème de ce principe est que le nombre de modifications peut devenir grand.

A la fin de la première partie du livre de Kent Beck, on obtient un petit programme en java avec 5 objets et un ensemble de tests unitaires associés à ces objets. Jester trouve très facilement la seule méthode non testée, laissée ainsi volontairement par l’auteur. Pour le reste Jester montre que le code est bien couvert par les tests unitaires. L’ajout du test manquant est assez simple. Au final, le développeur est satisfait car il a été plus loin qu’écrire du simple code, il tente de prouver que son code est exact.
En fait, il faut relativiser le montre joie car générer les mutants n’est pas simple. Jester se base sur un ficher de configuration « mutations.jcg ». Lorsqu’on regarde le nombre de mutants générés dans l’exemple de Kent Beck avec la la configuration par défaut de Jester, seuls 5 mutants ont été générés et sur les 5 classes deux n’avaient pas de mutants. En modifiant ce fichier, j’ai réussit à passer à 8 mutants et à trouver une autre méthode non couverte par les tests. Mais encore une fois l’écriture du test était très simple.

Maintenant, le problème est toujours de passer d’un exemple de démonstration à un cadre réel de travail. Pour ma part, j’en suis encore loin car les tests unitaires sont rarement écrits dans le cadre de mon travail. Donc avant de tester les tests, il faudrait déjà les écrire…

Le site de jester est http://jester.sourceforge.net/. la dernière version est la 1.37 datant de février 2005. Depuis plus rien, mais la version est question est un peu rudimentaire mais utilisable. Les transpositions pour Python (Pester) et C# (Nester) semblent abandonnés. Si vous avez Python d’installer vous pouvez profiter de rapport sous format html, vous indiquant clairement les parties de code non testées.

Retrouver jar à partir du nom d’une classe

mai 13, 2007

Le site suivant www.jarfinder.com permet de retrouver l’éventuel jar manquant dans une application java. A partir du nom d’une classe, il permet de retrouver les jars contenant cette classe. Ce petit utilitaire, j’en suis persuadé sera utile à tous les développeurs java.

Hammurapi outil de contrôle de code java

janvier 16, 2007

Hammurapi est un outil d’inspection automatique du code java. Il vérifie que votre code respecte certaines préconisations dont celles de SUN. Il est possible de modifier ces règles ou d’en ajouter. Hammurapi est un outil open source. La version stable actuelle est la 3.19.1.2, l’archive fait 14,7 Mo et se trouve sur le site de ce projet. L’utilisation « la plus basique » est assez simple. Il faut décompresser l’archive. Ensuite, il faut suivre l’exemple « template » du répertoire projects. Alors, placer dans le répertoire projects\template\src l’ensemble sur source java et dans le répertoire projects\template\lib les librairies nécessaires au projet. Enfin, lancer la commande ant (qui doit donc être installé sur le poste) dans le répertoire projects\template. Hammurapi va compiler le projet, créer la javadoc et enfin contrôler le code.

Le résultat se trouve dans le répertoire project\template\review sous forme html (summary.html). Les règles sont classées en trois groupes selon la sévérité. Par la suite, il est possible de modifier les répertoires sources ou d’intégrer Hammurapi à l’éditeur Eclipse.