Il y a 13 ans -
Temps de lecture 6 minutes
Configurer vos projets SBT pour Eclipse ou IntelliJ IDEA
Dans la lignée du premier article consacré à la présentation de l’outil sbt pour Scala, ce second article s’intéressera à la configuration de nos projets sbt.
Objectif : pouvoir les importer dans nos IDEs Scala préférés (surtout les miens ;-) ) à savoir IntelliJ IDEA (Community ou Ultimate Edition) et Eclipse. Git et sbt sont les seuls composants pré-requis pour ce tutoriel.
Nous allons ainsi entrevoir le mécanisme de plugin de sbt ainsi que l’application de plugins sur un projet sbt. Pour celles et ceux qui connaissent un minimum ces deux environnements de développement, rien de bien sorcier : ajouter une facet Scala au projet, définir certains répertoires en tant que répertoires sources, d’autres en tant que répertoires de tests, définir _lib_managed_ en tant que dossier de librairies… Il est donc tout à fait possible de faire tout ceci à la main en quelques minutes. L’idée ici est vraiment de jouer avec quelques plugins sbt et les intégrer à un projet existant.
Si vous êtes plutôt Emacs ou Vim, je vous renvoie sur le site de sbt pour la configuration à adopter.
Eclipse
Nous allons importer notre projet à l’aide du plugin SbtEclipsify. Ce plugin prend en charge la création de tous les fichiers nécessaires à Eclipse .project,.classpath…) afin que le projet soit importable et intégralement configuré. Il n’est actuellement disponible sur aucun repository, il va donc falloir soit télécharger le Jar et le déposer dans son repository local, soit récupérer le projet et utiliser sbt pour le compiler et le publier en local. Nous partirons sur ce deuxième choix (pour utiliser quelques petites commandes sbt).
Tout d’abord, nous allons récupérer le projet à l’aide de la commande git clone
:
$ git clone http://github.com/musk/SbtEclipsify.git
Ensuite, nous allons démarrer sbt et faire un update
pour mettre à jour toutes les dépendances du projet :
$ sbt $ update

Nos dépendances étant à jour, nous allons pouvoir compiler et publier le projet à l’aide de la commande publish-local
(image tronquée) :
$ publish-local

Maintenant que le Jar est disponible dans notre repository, nous allons pouvoir configurer notre projet avec cette nouvelle dépendance. Pour cela, créons le fichier project/plugins/Plugins.scala
et ajoutons le plugin sbt-eclispsify :
import sbt._ class MySbtProjectPlugins(info: ProjectInfo) extends PluginDefinition(info) { lazy val eclipse = "de.element34" % "sbt-eclipsify" % "0.5.2-SNAPSHOT" }
Dernière étape avant de tout builder : modifier notre fichier projet, dans la classe project/build/MyProject.scala
, pour marquer notre projet en tant que projet eclipsifiable à l’aide du trait Eclipsify
:
import sbt._ import de.element34.sbteclipsify._ class MyProject(info: ProjectInfo) extends DefaultProject(info) with Eclipsify { // ... }
Voilà, tout est prêt, démarrons sbt et lançons la commande eclipse
après avoir mis à jour nos dépendances pour notre projet (à l’aide de la commande update
) :
$ sbt $ update $ eclipse

That’s all ! Il n’y a plus qu’à faire un import dans Eclipse de votre projet. A partir de maintenant, la commande eclipse
ne devrait plus vous servir. Il faudra dès lors passer par reload
lors de modifications concernant vos plugins ou vos dépendances pour mettre à jour votre contexte sbt et bien sûr update
pour la mise à jour de vos dépendances.

A noter que d’autres plugins existent :
- sbt-eclipse-plugin : ce plugin n’est ni plus ni moins qu’un container de type classpath qui pointe vers le dossier
lib_managed
. L’outil fonctionne très bien mais les manipulations sont à effectuer à la main et aucune opération en ligne de commande (pour automatisation) n’est disponible pour l’instant. A surveiller donc ; - IvyIDE (avec la procédure d’installation ici).
IntelliJ IDEA
Plusieurs plugins existent et, pour ma part, j’ai choisi le plugin sbt-idea-plugin. A noter que celui-ci fournit son propre repository maven donc pas de git clone
sur le projet avec un publish-local
comme pour SbtEclipsify. Tout se fait cette fois-ci très simplement !
Comme pour SbtEclipsify, le plugin fournit un trait qu’il faudra ajouter à sa classe projet qui lui permettra d’avoir la commande idea
disponible dans le shell.
Il faut donc tout d’abord se rendre dans la classe project/plugins/Plugins.scala
et ajouter ces quelques lignes. Elles ajouteront un repository distant et la dépendance du plugin :
val repo = "GH-pages repo" at "http://mpeltonen.github.com/maven/" val idea = "com.github.mpeltonen" % "sbt-idea-plugin" % "0.1-SNAPSHOT"
Maintenant que notre plugin est prêt à l’emploi, nous allons l’ajouter dans la configuration de notre projet (toujours au niveau de project/build/MyProject.scala
). Cela nous donne :
import sbt._ import de.element34.sbteclipsify._ class MainProject(info: ProjectInfo) extends ParentProject(info) with IdeaPlugin { lazy val myProject = project("myproject", "My Project", new DefaultProject(_) with IdeaPlugin) // ... }
Grosse différence avec Eclipse : le plugin fonctionne par défaut, même si l’on a qu’un seul project, comme une arborescence de projets. Ainsi, nous aurons un projet parent composé de sous-projet(s). Pour utiliser ce plugin, nous allons donc (cf. code ci-dessus) créer un projet MainProject
en tant que conteneur de projet en étendant ParentProject
. Ensuite, nous créerons dans ce projet sbt un projet de type DefaultProject
qui contiendra notre code ({{src/main/scala}}…).
Notez que les deux projets utilisent le trait IdeaPlugin
. En effet, IntelliJ IDEA gère parfaitement l’arborescence de projets. Nous aurons donc les deux projets importés dans l’IDE avec la vue projets qui nous affichera le projet parent et notre projet.
A ce niveau, comme pour Eclipse, tout est prêt ! Donc un update
et cette fois-ci un idea
pour lancer le plugin :
$ sbt $ update $ idea

Et le résultat avec notre projet parent contenant notre sous-projet une fois importé dans IntelliJ IDEA (par le fichier .ipr
) :

Les deux ?
Et si tout comme moi, cela vous arrive de switcher de l’un à l’autre selon votre humeur (tiens aujourd’hui j’ai envie de faire du Eclipse :-) ), vous pourrez bien évidemment configurer votre projet pour qu’il accueille ces deux environnements de développement. La configuration finale sera un mix de ce que l’on a vu précédemment. En ne prenant pas le projet parent en tant que projet Eclipse (car il ne les gère pas très bien), cela nous donne tout simplement :
class MainProject(info: ProjectInfo) extends ParentProject(info) with IdeaPlugin { lazy val myProject = project("myproject", "My Project", new MyProject(_) with IdeaPlugin with Eclipsify) class MyProject(info: ProjectInfo) extends DefaultProject(info) { // Put here MyProject dependencies } }
Cette configuration fonctionne out-of-the-box pour IntelliJ IDEA, par contre pour Eclipse un problème de build path subsiste. Il est directement lié à cette arborescence de projets (module / sous-module) qui n’est actuellement pas géré par le plugin :

Il faudra donc modifier à la main le build path de notre projet. Une fois celui-ci modifié, le projet sera opérationnel pour Eclipse et vous n’aurez plus qu’à faire des sbt update
pour mettre à jour vos dépendances :

Dernière chose, entre la configuration pour avoir les deux plugins et celle d’IntelliJ IDEA standalone : notez la différence concernant le sous-projet MyProject
avec non plus l’utilisation directe d’une nouvelle instance de DefaultProject
mais la création et l’instanciation d’une nouvelle classe MyProject
qui étend DefaultProject
. Cela va nous permettre de définir des dépendances uniquement au niveau du sous-projet et ainsi ne pas tout mettre au niveau du projet parent. Il est dès lors possible d’ajouter plusieurs sous-projets à MainProject
et ainsi se retrouver avec le même type d’arborescence de modules que l’on retrouve dans nos projets maven.
Vous pouvez toujours récupérer le petit projet scala-samples qui possède cette double configuration idea/eclipse.
Commentaire