12 KiB
Cette page a été importée automatiquement de notre ancien wiki mais n'a pas encore été révisée.
Howto Rails
http://blog.phusion.nl/2012/09/21/the-right-way-to-deal-with-frozen-processes-on-unix/
Mettre en place un environnement de production "Ruby On Rails" exige de trouver les bons compromis entre les composants système - stable et robuste par nature - et l'environnement de développement "Ruby On Rails" très volatile et changeant. Voici comment nous mettons cela en oeuvre.
Cas 1 : utilisation avec Passenger
- Documentation de Passenger pour Apache
- Documentation de Ruby Enterprise Edition
- Un howto pour Yaml (en parallèle avec Ruby, mais simple à comprendre)
Installation
On installe d'abord Ruby 1.8 et ses dépendances utiles (irb
, rdoc
, ri
, …).
# aptitude install ruby-full irb rubygems rails libactionpack-ruby1.8 libactionmailer-ruby1.8
Installer les bindings MySQL et OpenSSL (voir [#les-gems Les gems]) :
# aptitude install libmysql-ruby libopenssl-ruby libmysqlclient15-dev
Les gems #les-gems
Les gems sont des paquets contentant des librairies et/ou des applications écrites en Ruby. Elles sont énormément utilisées, notamment dans Rails.
Par défaut, aucune librairie n'est installée sous forme de gem à part les bindings MySQL et Rack (qui est une dépendance de Passenger)
Il est préférable d'installer les bindings MySQL à la main (libmysql-ruby
) car ils nécessitent la compilation d'extensions en C et
risquent d'être utilisés par tous les utilisateurs.
OpenSSL fait normalement partie de la librairie standard Ruby, mais n'est pas inclus dans Debian. Rails en a besoin pour fonctionner, il convient
donc d'installer libopenssl-ruby
manuellement.
Ruby Enterprise Edition (REE)
REE est une version patchée de Ruby optimisée pour les applications Web et créée par les mêmes développeurs que Passenger. REE est donc censé s'intégrer parfaitement avec Passenger.
Des paquets (ubuntu) existent pour REE, mais le plus simple est de le compiler à la main.
Par défaut il s'installera dans le dossier /opt
, en totale isolation du reste du système.
Rubygems est livré avec REE, et est placé dans le dossier de ce dernier.
Il suffit de récupérer une archive des sources sur le site de REE,
de la décompresser et de lancer le script ./installer --no-dev-docs
en tant que root. Le reste de la procédure est indiqué
par l'installateur.
À noter qu'il faut avoir installé les paquets libreadline-dev
, libz-dev
, libssl-dev
et avoir une suite de
compilation fonctionnelle (gcc, g++, make, patch, …)
Utilisation avec Passenger
Passenger est livré avec REE sous forme de gem, on peut donc l'installer juste après REE. Le mode d'installation est alors quelque peu différent :
Avant tout on installe toutes les librairies nécessaires : celles de REE listées précédemment, plus les libs de développement d'Apache
# aptitude install libreadline-dev libz-dev libssl-dev apache2-prefork-dev libcurl4-openssl-dev
On installe ensuite REE selon la procédure définie ci-dessus, et une fois cette installation terminée, on lance la commande :
/opt/ruby-enterprise-<version>/bin/passenger-install-apache2-module
L'installateur nous guide dans la procédure. Dans le cas ou le MPM d'Apache est ITK, il préviendra :
WARNING: Apache doesn't seem to be compiled with the 'prefork' or 'worker' MPM
On peut cependant continuer l'installation en ignorant l'avertissement. Une fois terminée, l'installateur donne la configuration pour Apache
Dans /etc/apache2/mods-available/passenger.load
on mettra la ligne :
LoadModule passenger_module /opt/ruby-enterprise-1.8.7-2010.02/lib/ruby/gems/1.8/gems/passenger-3.0.0/ext/apache2/mod_passenger.so
et dans /etc/apache2/mods-available/passenger.conf
:
<IfModule passenger_module>
PassengerRoot /opt/ruby-enterprise-<version>/lib/ruby/gems/1.8/gems/passenger-3.0.0
PassengerRuby /opt/ruby-enterprise-<version>/bin/ruby
PassengerEnabled off
#RailsAutoDetect off
#RackAutoDetect off
PassengerFriendlyErrorPages off
</IfModule>
Puis : a2enmod passenger
Une fois REE installé il reste un dernier soucis, les binaires sont dans /opt/ruby-enterprise-<version>/bin
,
et pour que les utilisateurs puissent les utiliser il y a deux options possibles :
- Rajouter ce chemin dans le PATH par défaut de tous les utilisateurs.
- Créer des liens symboliques dans
/usr/bin
.
Pour la deuxième solution, le script suivant permet d'automatiser la tâche :
#!/bin/bash
cd /usr/bin
for i in `ls -1d /opt/ruby-enterprise-*/bin/*`; do
ln -s $i
done
Configuration de Passenger/mod_rails
Par défaut, Passenger est activé pour tous les sites d'Apache et propose une auto-détection des environnements Rails et Rack,
on commence par désactiver ce comportement dans /etc/apache2/mods-available/passenger.conf
:
<IfModule mod_passenger.c>
PassengerRoot /usr
PassengerRuby /usr/bin/ruby1.8
# On ajoute les lignes suivantes:
PassengerEnabled off
RailsAutoDetect off
RackAutoDetect off
PassengerTempDir /var/tmp/
PassengerUploadBufferDir /var/tmp
# S'assurer que les permissions sur le dossier permettent à Apache d'écrire dedans
# cf. <http://modrails.com/documentation/Users%20guide%20Apache.html#PassengerUploadBufferDir>
# C'est surtout important avec Apache ITK !
</IfModule>
Exemple de VirtualHost pour Rails
<VirtualHost *:80>
ServerName redmine.evolix.net
PassengerEnabled on
RailsAutoDetect on
DocumentRoot /home/redmine/www/public
<Directory /home/redmine/www/public>
Allow from all
Options -MultiViews
</Directory>
# Pour Apache 2 ITK
AssignUserID {user} {group}
</VirtualHost>
- [#apache-itk-users Information complémentaire sur Apache ITK]
- Script de génération de VHost
Trucs, astuces et détails
Apache ITK #apache-itk-users
Passenger détermine sous quel utilisateur il va lancer l'application en se basant sur le propriétaire du fichier
config/environment.rb
de l'application Rails.
Il faut donc y placer un propriétaire identique à celui utilisé dans AssignUserID
Les environnements de Rails
Rails propose trois environnements d'exécution distincts : production
, development
et test
.
Chacun a un but précis facilement devinable depuis son nom.
Par défaut, Passenger fait tourner l'application en mode production. On peut forcer un certain environnement
en plaçant la directive RailsEnv <env>
dans le fichier de configuration du VHost.
Pour lancer dans un certain environnement les commandes qui agissent avec l'application (par exemple les tâches Rake), il suffit de définir la variable d'environnement RAILS_ENV, par exemple :
$ RAILS_ENV=production rake db:migrate
Redémarrage de l'application
Pour redémarrer une application Rails, il suffit de créer ou de mettre à jour le timestamp du fichier
tmp/restart.txt
(avec la commande touch
par exemple). À la prochaîne requête, l'application sera
redémarrée et tout l'environement chargé de nouveau.
Pour que l'application redémarre à chaque requête on peut aussi créer un fichier tmp/always_restart.txt
et le supprimer une fois qu'on ne souhaite plus ce comportement.
umask
s spéciaux
Sur certains système, l'umask par défaut rend les fichiers installés par root non lisibles par le commun des utilisateurs.
Si celà est une bonne idée, combinée avec Rubygems et Apache ITK, celà devient moins évident, et il faut veiller
à chmod
er correctement le dossier de Ruby pour que tous les utilisateurs puissent l'utiliser.
Un exemple avec REE :
# chmod -R u=rwX,g=rX,o=rX /opt/ruby-enterprise-1.8.7-2010.02/
Priorités de chargement
Par défaut, même lorsque rubygems
est activé, Ruby utilisera en priorité les librairies système
(celles installées par les paquets) plutôt que les gems. On peut cependant forcer l'utilisation d'une gem,
et même fixer la version désirée (sinon c'est la plus récente qui est automatiquement utilisée).
Cette gestion des versions doit être faite par le développeur, qui peut installer les librairies qu'il souhaite indépendamment du système. L'important est de savoir qu'il y a trois endroits ou on peut trouver une librairie Ruby :
- Installée par un paquet (
/usr/lib/ruby/1.8/
) - Installée en temps que gem système (
/var/lib/gems/1.8/
) - Installée en temps que gem utilisateur (
~/.gem/ruby/1.8/
)
Lister les gems
Il n'existe pas de moyen de lister les gems installées uniquement sur le système, la commande gem
cherche
à la fois dans le dossier .gem
de l'utilisateur et le dossier système. La solution est d'utiliser un script
spécialisé qui fait cette recherche.
Le script est disponible dans le dépôt Subversion du Pack Web Evolix, dans trunk/scripts/list_gems.
Économiser un peu d'espace
Par défaut, gem
installe la documentation aux formats RDoc (documentation html) et RI (documentation console)
pour les gems installées. Pour éviter celà, créer un fichier .gemrc
dans la $HOME
de l'utilisateur avec le
contenu suivant :
gem: --no-rdoc --no-ri
À mettre aussi dans la $HOME
de root
si c'est lui qui installe les gems.
Rails 2.3.2->2.3.5 & Passenger & les logs
Une petite erreur en environnement de production affecte les versions 2.3.2 à 2.3.5 (incluse) de Rails. Les logs
de l'application ne sont pas écrits dans le fichier log/production.log
. Pour pallier cette erreur, il faut appliquer
le patch qu'on trouve ici
(deuxième fichier).
Répertoire temporaire de Passenger
Passenger stocke tous ses fichiers temporaires dans le répertoire /tmp/ par défaut. Pour diverses raisons (de place, de droits voire de performance), il peut être intéressant d'en définir un autre. Cela ce fait via la directive Apache du module Passenger PassengerTempDir. Par exemple, nous mettons :
PassengerTempDir /var/tmp/
Mise à jour de Passenger
Passenger est installé en tant que gem dans /opt/ruby-enterprise-/lib/ruby/gems/1.8/gems/. Voici la procédure pour le mettre à jour :
gem update passenger
/opt/ruby-enterprise-<version-ree>/lib/ruby/gems/1.8/gems/passenger-<nouvelle-version-passenger>/bin/passenger-install-apache2-module
Puis modifier les chemins vers mod_passenger dans la conf d'Apache /etc/apache2/mod-available/passenger.{conf,load} pour pointer vers la nouvelle version (notamment les directives LoadModule et PassengerRoot). Enfin, redémarrer Apache pour prendre en compte le nouveau module.
Mise à jour de REE
Pour mettre à jour REE, il suffit de recommencer la procédure d'installation, la nouvelle version sera installé dans /opt/ruby-enterprise- et ne perturbera donc pas la prod existante.
Pour prendre en compte la nouvelle installation de REE, il faut modifier les chemins vers REE dans la configuration d'Apache.
Important : pour la migration de REE 1.8.7-2010.02 vers 1.8.7-2011.01, il faut ajouter cette directive dans la configuration d'Apache :
RackBaseURI /
Et enlever les éventuelles directives RailkBaseURI
.
Cas 2 : utilisation avec rbenv + Unicorn
rbenv permet d'avoir un environnement compilé par utilisateur. C'est donc le développeur qui gère sa version de Ruby, ses Gems, etc... on ne lui installe même pas Ruby !
Note préalable : mettre les droits exec sur la partition /home
# aptitude install build-essential curl mg
# aptitude install python-pygments zlib1g-dev libxml2-dev \
libxslt1-dev libmysqlclient-dev libcurl4-openssl-dev \
libmagickcore-dev libmagickwand-dev libreadline-dev imagemagick
$ git clone git://github.com/sstephenson/rbenv.git .rbenv
$ git clone git://github.com/sstephenson/ruby-build.git .rbenv/plugins/ruby-build
$ echo 'export PATH="$HOME/.rbenv/bin:$PATH"' >> ~/.bash_profile
$ echo 'eval "$(rbenv init -)"' >> ~/.bash_profile
$ . .bash_profile
$ rbenv install 1.9.2-p290
$ rbenv global 1.9.2-p290
Astuces diverses :
rails_env = `head -1 $(HOME}/www/current/config/database.yml | tr ':' ' '`