Important

Depuis l’écriture de ce billet j’ai trouvé plus intéressant de s’affranchir de RVM qui n’est finalement pas obligatoire pour pouvoir utiliser Sass et Compass.
En effet, les développeurs du préprocesseurs portent un soin particulier à la compatibilité de l’outil avec les différentes version de Ruby. Ainsi, je n’utilise plus que Bundler pour gérer mes versions des gems dans mes projets.
L’installation et l’utilisation de Bundler dans des projets Sass/Compass est détaillée dans le chapitre 6 du livre Sass et Compass avancé.

Maintenir un environnement de développement est toujours délicat lorsqu’il doit convenir à plusieurs projets et leurs pré-requis. Cela se vérifie d’autant plus qu’il nous faut désormais jongler avec des projets hybrides (PHP, Ruby, Node.js, etc). Le cas de figure se rencontre lorsque des projets PHP font appels au préprocesseur Sass et Compass, son framework CSS3, tous deux en Ruby.

Les amateurs de Ruby dirons que des outils existent pour simplifier la tâche. Et ils ont raison ! Cependant, tout le monde n’est pas rubiste dans l’âme et c’est pourquoi je vous présentais il y a quelques mois une méthode pour maintenir plusieurs versions de Compass. Je reviens sur cette question épineuse parce que je suis arrivé à la limite de la solution.
En effet, je dois aujourd’hui gérer de nombreuses versions de Compass disséminées dans bien des projets. Et autant le dire clairement, consulter un README pour me rafraîchir la mémoire quant à la version de Compass (et autres outils en Ruby) requise par un projet me fatigue. Il en va de même pour mes collègues.

Heureusement pour nous, l’évolution des outils que sont RVM et Bundler offre désormais une gestion simplifiée de projets Sass et Compass, voire automatisée !

Mettre à jour RVM

Avant toute chose, vérifiez votre version de RVM :

$ rvm --version

Puis suivant la version retournée :

  • supérieure ou égale à 1.10.3, vous pouvez passer directement à la section suivante. Je vous conseille néanmoins de donner un coup de fraîcheur à votre RVM :)
  • inférieure à 1.10.3, il va vous falloir mettre à jour RVM.

Afin de profiter des dernières améliorations de RVM, il vous faut le mettre à jour, ce qui résume à relancer une installation du script :

$ cd
$ \curl -L https://get.rvm.io | bash -s stable

L’antislash en début de la commande curl n’est pas une erreur, veillez à le saisir.

La mise à jour réalisée, re-chargez RVM (ou ouvrez une nouvelle fenêtre de terminal) :

$ rvm reload

Pour information, vous pourrez désormais mettre à jour RVM à l’aide de la commande rvm get stable :

$ rvm get stable
$ rvm reload

Important :
Je ne fais pas appel à la commande sudo, vous non plus ! RVM s’installera ainsi dans votre espace utilisateur et vous affranchira de l’appel à sudo pour un oui ou pour un non (pour simplifier).

Gestion par projet des versions de Sass et Compass

La gestion simplifiée de la version de notre pré-processeur CSS préféré est le résultat de 2 évolutions de RVM :

  1. RVM installe la gemme Bundler en cas de besoin.
  2. À chaque ouverture de dossier, RVM vérifie la présence d’un fichier Gemfile et le cas échéant le parse pour identifier la version de ruby et le gemset à charger.

Gestion des dépendances avec Bundler

Bundler nous permet de maintenir les dépendances Ruby (les gemmes) d’un projet à l’aide d’un simple fichier j’ai nommé Gemfile :

source :rubygems
gem "compass"
gem "oily_png"

La syntaxe de cet exemple est concise, mais retenez que Bundler offre bien plus d’options. Ici, on indique simplement que le projet nécessite les dernières versions connues de Compass et la gemme OilyPNG.

Si vous devez employer une version spécifique d’une gemme, il est possible de la préciser :

source :rubygems
gem "compass", "0.12.1"
gem "oily_png"

voire même d’indiquer à Bundler que le projet accepte toute nouvelle version mineure à l’aide du sélecteur pessimiste ~> (connu sous le doux nom de spermy operator) :

source :rubygems
gem "compass", "~> 0.12.1"
gem "oily_png"

Plus clairement, toute version supérieure ou égale à 0.12.X et strictement inférieure à 0.13 sera acceptée. Une définition équivalente est donc ">= 0.12.1", "< 0.13".

Le fichier Gemfile est a déposer à la racine du répertoire depuis lequel vous lancez Sass ou Compass. Ainsi, RVM le chargera dès que vous vous positionnerez dans le répertoire.

Dédier un gemset par projet avec RVM

Maintenir de multiples gemsets (idéalement un par projet même si en pratique on en crée un par version de Compass) est chronophage et peu être source d’erreurs. Surtout lorsqu’il y a plusieurs intervenants sur le projet ; les configurations des machines et des gemmes installées n’étant pas obligatoirement identiques.

C’est pourquoi RVM a évolué pour supporter des commentaires spécifiques dans le fichier Gemfile afin de déterminer la version de Ruby ainsi que le nom du gemset à charger pour le répertoire courant :

source :rubygems

#ruby=1.9.2
#ruby-gemset=customer1-project1

gem "compass", "~> 0.12.1"
gem "oily_png"

En pratique, lorsque vous vous positionnez dans un dossier (en shell, of course), RVM lit le fichier Gemfile et

  • charge la version de Ruby requise ;
  • charge ou à défaut crée le gemset précisée.

Vous avez bien lu, RVM va permettre la création d’un gemset dédiée à votre projet si celui-ci venait à manquer :)
Un exemple, en supposant que mon fichier Gemfile est déposé dans projects/my_project/ :

$ cd projects/
$ rvm gemset name
/Users/mehdi/.rvm/gems/ruby-1.9.2-p320
$ cd my_project/
$ rvm gemset name
customer1-project1
$ cd ..
$ rvm gemset name
/Users/mehdi/.rvm/gems/ruby-1.9.2-p320

Note :
La version de Ruby est obligatoire et peut être précise : #ruby=ruby-1.9.2-p320.

Si la version de Ruby requise est absente de votre environnement, RVM vous invite a l’installer et bien évidemment aucun gemset n’est créé :

$ cd my_project2/
ruby-1.9.2-p290 is not installed.
To install do: 'rvm install ruby-1.9.2-p290'

Enfin, tout sous-répertoire d’un projet hérite du gemset demandé à RVM.

Initialisation du projet

Le fichier Gemfile étant créé, déplacez-vous à sa racine puis lancez l’installation des gemmes du projet à l’aide de la commande bundle install :

$ cd projects/my_project/
$ ls
  foo/   bar/  Gemfile
$ bundle install
  …
$ ls
  foo/   bar/  Gemfile  Gemfile.lock

Les gemmes sont désormais installées et un nouveau fichier Gemfile.lock est créé. Ce dernier est une sorte d’instantané des versions des gemmes employées, qui accélère les futures gestion de dépendances. Il permet surtout de s’assurer qu’une tierce personne installera via Bundler des versions identiques des gemmes.
Ce fichier est donc lui aussi à versionner.

Automatisation

Chaque projet possédera désormais son gemset dédié sans trop se fatiguer. C’est très bien, mais peut mieux faire. En effet, il nous faut lancer l’installation des gemmes manuellement et maintenir leurs mises à jour lorsque les besoins du projet évoluent (à l’aide d’un bundle install).

Cette tâche est automatisable en ajoutant dans votre fichier ~/.rvmrc la ligne :

rvm_autoinstall_bundler_flag=1

Dès lors, RVM va systématiquement lancer la commande bundle install lorsqu’il rencontre un fichier Gemfile \o/
Attention cependant, autant un pur intégrateur y verra un intérêt, autant un développeur qui checkout régulièrement des projets Ruby par simple curiosité n’activera pas cette option : il ne souhaitera pas pourrir son environnement Ruby par défaut de toutes les gemmes requises par les dits projets.

Supprimer le gemset d’un ancien projet

Voici la marche à suivre pour supprimer un gemset dédié a un projet qui s’est (bien — naturellement ;) ) terminé et pour lequel vous n’aurez plus à intervenir.

En premier lieu, et ce depuis n’importe quel emplacement, affichez la liste des gemsets :

$ rvm list gemsets

rvm gemsets

=> ruby-1.9.2-p180 [ x86_64 ]
   ruby-1.9.2-p180@global [ x86_64 ]
   ruby-1.9.2-p320 [ x86_64 ]
   ruby-1.9.2-p320@customer1-project1 [ x86_64 ]
   ruby-1.9.2-p320@customer1-project2 [ x86_64 ]
   ruby-1.9.2-p320@customer2-project1 [ x86_64 ]
   ruby-1.9.2-p320@customer3-project1 [ x86_64 ]
   ruby-1.9.2-p320@customer4-project1 [ x86_64 ]
   ruby-1.9.2-p320@global [ x86_64 ]

Vous souhaitez supprimer le gemset dédiée au projet customer3-project1 :

$ rvm gemset delete customer3-project1
/Users/mehdi/.rvm/gems/ruby-1.9.2-p180@customer3-project3 did not previously exist. Ignoring.

sans succès… Effectivement, une lecture attentive du listing précédent nous informe que la version de Ruby active est ruby-1.9.2-p180 alors que la version associée à votre gemset est ruby-1.9.2-p320. Lancez maintenant la commande en précisant le couple version_de_ruby@gemset (bref, un copié/collé) :

$ rvm gemset delete ruby-1.9.2-p320@customer3-project1
Are you SURE you wish to remove the entire gemset directory 'customer3-project1' (/Users/mehdi/.rvm/gems/ruby-1.9.2-p320@customer3-project1)?
(anything other than 'yes' will cancel) > yes
Removing gemset customer3-project1

Tout simplement :)

publicité (chargement)

4 réponses pour Gestion avancée de Sass et Compass avec RVM et Bundler

  1. Johan dit :

    Merci pour les explications d’utilisation de bundler pour Compass, j’utilisais déjà Bundle pour répliquer la configuration des mes environnements de dev entre eux, mais je ne connaissais pas les gemsets.

    En revanche, je reste dubitatif sur l’automatisation de la commande “bundle install” à chaque fois qu’un fichier bundle est dans le répertoire courant, je le recommanderai pas et j’exécuterai la commande à la main lorsque cela sera nécessaire.

  2. Vincentv dit :

    Bonjour,

    Tu n’as pas besoin d’utiliser RVM, surtout si tu n’utilise pas différentes version de ruby. Bundler est suffisant, il faut juste le configurer.

    dans le fichier ~/.bundle/config tu configure le path ou seront installer les gems dans ton projet, ex :

    BUNDLE_PATH: vendor/bundle

    Ensuite tu utilise bundle exec (http://goo.gl/1sXiz) pour executer une commande dans le contexte du projet, ex : bundle exec compass create.

    Il y a aussi la possibilité de se passer de bundle exec : https://github.com/gma/bundler-exec

  3. piouPiouM dit :

    @Johan (au cas où) les gemsets sont gérées par RVM et non Bundler. Concernant le lancement automatique de la commande bundle install je suis du même avis, je vais certainement reformuler ce passage :)

  4. piouPiouM dit :

    @Vincentv, merci pour la précision ! J’avoue être passé très tôt à RVM (même si je fais peu de Ruby). D’ailleurs il permet de s’affranchir de bundle exec en installant automatiquement la gemme rubygems-bundler.

    Après quelques tests et un peu de pratique, je remanierai ce billet pour y incorporer la gestion par Bundler exclusivement.

Ajouter un commentaire


Syndication

Réseaux sociaux