Ce blog — désormais archivé — est en lecture seule. Rendez-vous sur mon nouveau site personnel.

Prendre un Café

L'espace d'expression de Nicolas Perriault

Aller au contenu | Aller au menu | Aller à la recherche

Keyword - ruby

Fil des billets

vendredi 8 mai 2009

Installer Redmine sous Ubuntu

Redmine est un gestionnaire de projet technique exploitant Ruby on Rails et très inspiré de Trac, mais qui le dépasse fonctionnellement sur plusieurs points, notamment avec une gestion multiprojets qui fait cruellement défaut à son inspirateur. Voyons comment installer et déployer la dernière version de la branche stable (0.8) sur une Ubuntu Hardy Heron LTS[1].

(Redmine Screenshot)

Toutes les opérations décrites ci-dessous se font en root, mais libre à vous d’utiliser sudo à chaque fois, ou une fois pour toutes en lançant la commande sudo -s.

En préambule, on installe les quelques paquets qui nous seront nécessaires[2] :

# apt-get install build-essential ruby ruby1.8-dev rake libopenssl-ruby \
  libmysql-ruby apache2-threaded-dev subversion git

Maintenant, on récupère les sources de Redmine[3], qu’on va installer dans /opt :

# svn co http://redmine.rubyforge.org/svn/branches/0.8-stable /opt/redmine-0.8
# ln -s /opt/redmine-0.8 /opt/redmine

On va ajouter les sources de la version 2.1.2 de rails[4] dans le répertoire vendor de l’application, afin de cloisonner autant que possible l’environnement qu’elle exploite :

# cd /opt/redmine
# wget -O rails.tar.gz http://github.com/rails/rails/tarball/v2.1.2
# tar xvzf rails.tar.gz && rm rails.tar.gz
# mv railsXXX vendor/rails

Créez maintenant une base de données (MySQL ou autre) dédiée à Redmine. Une bonne pratique est de créer également un utilisateur MySQL aux droits restreints à sa seule exploitation.

Ensuite, éditez le fichier config/database.yml afin de modifier les paramètres de connexion à la base de données précédemment créée.

On installe maintenant une version récente de rubygems, ce qui nous permettra d’installer passenger, une sorte de mod_rails permettant de déployer facilement des applications rails sur un serveur Apache :

# wget http://rubyforge.org/frs/download.php/56228/rubygems-1.3.3.tar.gz
# tar xvzf rubygems-1.3.3.tar.gz && rm rubygems-1.3.3.tar.gz
# ruby setup.rb
# rm -r rubygems-1.3.3

Vous pouvez maintenant lancer la tâche de création des tables :

# rake db:migrate RAILS_ENV="production"

Et remplir la base avec quelques données par défaut :

# rake redmine:load_default_data RAILS_ENV="production"

On installe donc passenger, qui au passage vous posera quelques questions très simples :

# gem install passenger

On installe le module apache pour prendre en charge passenger :

# passenger-install-apache2-module

Pour mapper un domaine - par exemple mon.domaine.tld - vers votre instance Redmine, il faut d’abord créer un VirtualHost apache dédié, par exemple dans le fichier /etc/apache2/sites-available/redmine :

<VirtualHost *>
  SetEnv RAILS_ENV production
  ServerName mon.domaine.tld
  DocumentRoot /opt/redmine/public
</VirtualHost>

Vous noterez que la racine publique du vhost pointe vers le dossier public de l’instance Redmine précédemment installée. N’oubliez pas non plus de déclarer le domaine dans votre fichier /etc/hosts :

127.0.0.1 mon.domaine.tld

On active maintenant le vhost et on relance Apache :

# a2ensite redmine
# /etc/init.d/apache2 restart

Une dernière petite chose, vous devez autoriser Apache à lire et écrire dans certains répertoires de l’instance Redmine, comme suit :

# cd /opt/redmine
# chown -R www-data:www-data files log tmp
# chmod -R ug+rw files log tmp
# chmod -R o-rw files log tmp

Voila, vous devriez avoir une instance totalement fonctionnelle de Redmine, accessible par le domaine que vous avez configuré.

En cadeau Bonux, le support de GMail et TLS pour l’envoi d’emails

Si vous désirez configurer l’envoi des emails en utilisant un (ou votre) compte GMail[5], voici la procédure :

Installez tout d’abord le support de TLS pour ActiveMailer :

# cd /opt/redmine
# ruby script/plugin install git://github.com/collectiveidea/action_mailer_optional_tls.git

Puis éditez le fichier config/email.yml :

production:
  delivery_method: :smtp
  smtp_settings:
    tls: true
    address: "smtp.gmail.com"
    port: '587'
    domain: "smtp.gmail.com"
    authentication: :plain
    user_name: "votreadresse@gmail.com"
    password: "votremotdepasse"

Relancez Apache pour que la modification soit effective.

Edit : Prise en compte de certaines remarques faites en commentaires.

Notes

[1] C’est la version qui propulse mon serveur.

[2] Ce sont les paquets qui m’ont été nécessaires, sur ma machine ; n’hésitez pas à remonter d’éventuels manques en commentaires.

[3] On installe ici la dernière branche stable disponible à l’heure où sont écrites ces lignes, la 0.8.

[4] Oui, il y a plus récent, mais Redmine 0.8 est conçu pour tourner avec cette version : autant limiter les risques d’incompatibilités.

[5] L’intérêt principal à mes yeux reste l’archivage de tous les éléments envoyés.

samedi 3 mars 2007

Ruby on Rails 1.2.2, les migrations

Voici la suite du précédent tutoriel sur Ruby on Rails publié sur ce même blog ou nous avons mis en place une application de gestion de contacts rudimentaire.

Migration de schéma de base de données

Imaginons que nous voulions gérer une liste de sociétés, et lier chacun de nos contacts à sa société... Il va nous falloir modifier notre base de données en ajoutant une table companies et une clé company_id dans la table contacts. Cela peut s'avérer compliqué puisqu'elle contient déjà des données... même si en l'occurence il ne s'agit pour l'heure que de données de test.

Rails et plus particulièrement ActiveRecord proposent un outil de gestion des évolutions du modèle de données intelligent, les migrations. Au même titre que nous avions créé le fichier db/migrate/001_contacts_development.rb pour définir le schéma initial lors du tutoriel précédent, nous allons maintenant créer son évolution incrémentale dans le fichier db/migrate/002_contacts_development.rb :

 ruby
class ContactsDevelopment < ActiveRecord::Migration
  
  def self.up
    # On renomme le champs name en first_name (ne devra contenir que le prénom)
    rename_column :contacts, "name",       "first_name"
    
    # Ajout d'un champs pour stocker le nom de famille
    add_column    :contacts, "last_name",  :string
    
    # Ajout d'un champs pour stocker la société du contact
    add_column    :contacts, "company_id", :integer
    
    # Création de la table des sociétés
    create_table "companies", :force => true do |t| 
      t.column "name",        :string
      t.column "description", :text
      t.column "url",         :string
    end 
  end 

  def self.down
    # Rétablissement de la colonne name
    rename_column :contacts, "first_name", "name"

    # Destruction de la colonne last_name
    remove_column :contacts, :last_name
    
    # Destruction de la colonne contenant la référence à une société
    remove_column :contacts, :company
    
    # Destruction de la table contenant les sociétés
    drop_table :companies
  end 

end

Dans chaque classe de migration de schéma, une méthode up appliquera des modifications au modèles tandis qu'une méthode down permettra un rollback des modifications vers une version antérieure. Pour le détail des opérations effectuées par le script de migration ci-dessus, je crois que les commentaires parlent d'eux-mêmes ;) (j'en ai profité pour répartir le patronyme sur deux champs, nom et prénom)

La mise à jour effective du modèle dans la base de données s'effectue grâce à la commande :

 bash
$ rake db:migrate 
(in /home/niko/ww2/rails/contacts)
== ContactsDevelopment: migrating =============================================
-- rename_column(:contacts, "name", "first_name")
   -> 0.0750s
-- add_column(:contacts, "last_name", :string)
   -> 0.0153s
-- add_column(:contacts, "company_id", :integer)
   -> 0.0343s
-- create_table("companies", {:force=>true})
   -> 0.0304s
== ContactsDevelopment: migrated (0.1694s) ====================================

Nous n'avons pas d'outils d'administration pour notre nouvelle table companies, créons-les :

$ ruby script/generate scaffold Company

Il faut maintenant mettre à jour notre jeu de données ; on édite d'abord le nouveau fichier ./test/fixtures/companies.yml :

 yaml
Nanonical:
  id:          1
  name:        Nanonical
  description: On vous préfère libres
  url:         http://www.nanonical.com
  
Crimosoft:
  id:          2
  name:        Crimosoft
  description: Notre monopole, c'est trop lol
  url:         http://www.crimosoft.com

Toute ressemblance avec des sociétés existantes ou ayant existé serait un sacré coup de pot

Puis, dans le fichier ./test/fixtures/contacts.yml :

 yaml
John:
  id:         1
  first_name: John
  last_name:  Doe
  email:      john@doe.com
  address:    12, rue des champs
  zip:        75009
  city:       Paris
  country:    France
  company_id: 1 # John -> Nanonical
 
Bob:
  id:         2
  first_name: Bob 
  last_name:  Doe 
  email:      bob@doe.com
  address:    1, place du pré 
  zip:        35000
  city:       Rennes
  country:    France
  company_id: 2 # Bob -> Crimosoft

On réinsère nos nouvelles fixtures :

$ rake db:fixtures:load

On peut se rendre successivement aux adresses http://0.0.0.0:3000/contacts et http://0.0.0.0:3000/companies afin de s'assurer que tout va bien.

companies_scaffolding.png

Mise à jour des classes modèles

Pour que Rails prenne en compte les modifications structurelles de notre schéma, nous allons éditer les fichiers des modèles Contact et Company, notamment pour spécifier leur type de relation grace aux méthodes de classe ActiveRecord.

Le fichier ./apps/models/contact.rb :

 ruby
class Contact < ActiveRecord::Base
  # Chaque employé appartient à une compagnie
  belongs_to :company
end

Et le fichier ./apps/models/company.rb :

 ruby
class Company < ActiveRecord::Base
  # Une société possède plusieurs employés
  has_many :contact
end

Mise à jour du contrôleur

On récupère la liste des sociétés depuis le contrôleur gérant les contacts (situé dans le fichier ./app/controllers/contacts_controller.rb), d'abord pour la création :

 ruby
class ContactsController < ApplicationController
  [...]
  def new
    @contact = Contact.new
    @companies = Company.find_all
  end

Puis pour l'édition:

 ruby
class ContactsController < ApplicationController
  [...]
  def edit
    @contact = Contact.find(params[:id])
    @companies = Company.find_all
  end

Mise à jour de la vue

Enfin, modifions notre formulaire d'édition/création de contacts, situé dans app/views/contacts/_form.rhtml, comme suit :

 rhtml
<%= error_messages_for 'contact' %>

<!--[form:contact]-->
<p><label for="contact_company_id">Company</label>
<%= select 'contact', 'company_id', @companies.collect {|c| [c.name, c.id]} %></p>

<p><label for="contact_name">First name</label><br/>
<%= text_field 'contact', 'first_name'  %></p>

<p><label for="contact_name">Last name</label><br/>
<%= text_field 'contact', 'last_name'  %></p>

<p><label for="contact_email">Email</label><br/>
<%= text_field 'contact', 'email'  %></p>

<p><label for="contact_address">Address</label><br/>
<%= text_field 'contact', 'address'  %></p>

<p><label for="contact_city">City</label><br/>
<%= text_field 'contact', 'city'  %></p>

<p><label for="contact_zip">Zip</label><br/>
<%= text_field 'contact', 'zip'  %></p>

<p><label for="contact_country">Country</label><br/>
<%= text_field 'contact', 'country'  %></p>
<!--[eoform:contact]-->

Ce qui donne à peu-près ceci :

Nouveau formulaire de création/édition de contacts

Et le template d'affichage de notre liste de contacts, dans le fichier ./app/views/contacts/list.rhtml pour y ajouter la colonne affichant le nom de la société pour chaque contact :

 rhtml
<h1>Listing contacts</h1>

<table>
  <tr>
  <% for column in Contact.content_columns %>
    <th><%= column.human_name %></th>
  <% end %>
    <th>Société</th>
  </tr>
  
<% for contact in @contacts %>
  <tr>
  <% for column in Contact.content_columns %>
    <td><%=h contact.send(column.name) %></td>
  <% end %>
    <td><%= h contact.company.name %></td>
    <td><%= link_to 'Show', :action => 'show', :id => contact %></td>
    <td><%= link_to 'Edit', :action => 'edit', :id => contact %></td>
    <td><%= link_to 'Destroy', { :action => 'destroy', :id => contact }, :confirm => 'Are you sure?', :method => :post %></td>
  </tr>
<% end %>
</table>

<%= link_to 'Previous page', { :page => @contact_pages.current.previous } if @contact_pages.current.previous %>
<%= link_to 'Next page', { :page => @contact_pages.current.next } if @contact_pages.current.next %> 

<br />

<%= link_to 'New contact', :action => 'new' %>

Ce qui donne au final quelque chose comme ceci :

Nouvelle liste de contacts

To be continued

Dans un prochain tutoriel, nous aborderons la validation de formulaires.

samedi 3 mars 2007

Ruby on Rails 1.2.2, premier contact

Je dois préparer une réunion technique sur Ruby on Rails, aussi je m'y remets doucement. J'en profite donc pour passer en revue la version 1.2.2 du framework par le biais d'un petit tutoriel. Je prends pour exemple la gestion d'un carnet d'adresses simplissime.

Installation sur Ubuntu

L'installation de rails sur Ubuntu est toujours aussi simple.

Création de l'application

Vos pouvez créer votre projet rails n'importe où sur votre disque dur, par exemple dans ~/rails :

$ cd ~ && mkdir rails
$ rails contacts

Le squelette de l'application contacts est créé sous la forme d'un répertoire contenant l'arborescence par défaut d'un projet vierge.

$ cd contacts

Pour tester votre projet vierge, vous pouvez lancer Webrick, un petit serveur HTTP écrit en ruby inclus dans les librairies du framework :

$ script/server

Faites pointer votre navigateur à l'adresse http://0.0.0.0:3000/ pour admirer la page par défaut du projet.

Capture d'écran

Configuration de l'accès aux données

Dans le fichier config/databases.yml, on définit nos paramètres de connexion au SGBD, ici MySQL :

 yaml
development:
  adapter:  mysql
  database: contacts_development
  username: root
  password: password
  host:     localhost
  socket:   /var/run/mysqld/mysqld.sock

N'oubliez pas de créer une base MySQL contacts_development, hein ;)

Création d'une table dans la base données

On va utiliser le système de migration propre à rails pour garantir une évolutivité de notre modèle de données :

$ ruby script/generate migration contacts_development

On édite le fichier généré dans db/migrate/001_contacts_development.rb :

 ruby
class ContactsDevelopment < ActiveRecord::Migration

  def self.up
    create_table "contacts" do |t| 
      t.column "name", :string
      t.column "email", :string
      t.column "address", :string
      t.column "city", :string
      t.column "zip", :string
      t.column "country", :string
    end 
  end 

  def self.down
    drop_table :contacts
  end 

end

On lance la migration, ce qui pour l'heure aura pour conséquence et pour l'heure de créer notre table contacts dans la base de données :

$ rake db:migrate

Création d'un jeu de données

Nous allons créer quelques fixtures pour peupler notre table et avoir quelque chose à se mettre sous la dent. Pour cela, on crée (ou modifie) un fichier test/fixtures/contacts.yml contenant les deux entrées :

 yaml
John:
  name:    John Doe 
  email:   john@doe.com
  address: 12, rue des champs
  zip:     75009
  city:    Paris
  country: France

Bob:
  name:    Bob Doe 
  email:   bob@doe.com
  address: 1, place du pré 
  zip:     35000
  city:    Rennes
  country: France

On insère les données dans la base :

$ rake db:fixtures:load

Ces données permettront par la suite de tester plus facilement l'application.

Scaffolding

On crée un module basique de gestion de nos contacts :

$ ruby script/generate scaffold Contact

Faites pointer votre navigateur sur http://0.0.0.0:3000/contacts pour tester les scripts générés automatiquement.

Scaffolding basique dans rails 1.2.2

Ce n'est effectivement pas très beau, vous avez raison, mais c'est déjà fonctionnel... et surtout, cela ne nous a pas pris plus de 5 minutes !

À suivre

On ne s'arrêtera pas en si bon chemin, le prochain volet de ce tutoriel fera notamment évoluer notre schéma de base de données... stay tuned !

samedi 25 mars 2006

FreeOnRails, un hébergement gratuit pour vos applications Rails

[via Scoopeo]

Je vous avais fait une fausse joie récemment en annonçant que free.fr allait proposer gratuitement Ruby on Rails sur les pages perso. Hélas, fausse alerte, et jusqu'à aujourd'hui, impossible de trouver un hébergeur gratuit proposant Ruby et son framework superstar...

Jusqu'à ce que FreeOnRails ouvre ses portes ;)

Seules conditions :

  • Posséder un nom de domaine dédié,
  • S'inscrire et poster une demande d'hébergement motivée sur le forum ad-hoc.

Les caractéristiques de l'hébergement proposé sont très interessantes :

  • Pas de pub,
  • 100 Mo d'espace,
  • 1 Go de bande passante mensuelle,
  • Un accès SSH,
  • FastCGI,
  • PHP5 & Perl (au cas où ?),
  • Bases MySQL 4.1.x illimitées,
  • Sous-domaines, comptes ftp et emails illimités.

vendredi 17 février 2006

Ruby on Rails sur les pages perso de Free

Il semblerait que Free se prépare à proposer Ruby on Rails sur leur service d'hébergement de pages personnelles... Si c'est avéré, ça sera un formidable tremplin pour ce framework efficace et pour le langage Ruby, réellement très attachant :)

Edit : Fake. Déçu !

vendredi 20 janvier 2006

Apprendre Ruby on Rails facilement

[ Via Typhon weblog ]

J'ai entre les mains l'un des petits derniers des éditions Eyrolles - décidemment très productifs ces temps-ci - Ruby on Rails. C'est la traduction française du fort réputé Agile Web Development with Rails initialement écrit par Dave Thomas et David Heinemeier Hansson (ni plus ni moins que l'auteur du framework).

Le livre est une mine d'informations illustrée d'exemples pratiques notamment par le biais de la réalisation d'une boutique en ligne en très peu de temps et d'opérations. L'ouvrage est clair, accessible, exhaustif et bourré d'humour. On y trouve une des meilleures introduction au design pattern MVC que j'ai pu lire, une reflexion pertinente sur les méthodologies de développement ainsi qu'un référentiel complet des fonctions usuelles Ruby/Rails.

Cerise sur le gâteau, un partenariat avec l'hébergeur Typhon a été établi afin de proposer une réduction de 50% sur leur offre d'hégergement Découverte Rails pour tout acheteur du livre.

Si vous vous interessez de près ou de loin à Ruby et plus particulièrement à Rails, vous pouvez acheter l'ouvrage les yeux fermés :-)

dimanche 8 janvier 2006

Interlude - Installer un blog Typo

En attendant le tutorial complet de la création d'une application avec Ruby on Rails et RadRails, voila de quoi patienter et découvrir un peu plus les possibilités du framework.

Les applications RoR fleurissent un peu partout ces temps-ci, et certaines sont assez bluffantes. Je viens de tomber sur Typo, un gestionnaire de Weblog très sympa écrit en Ruby et doté de fonctionnalités tout à fait interessantes :

  • Interface tout AJAX,
  • Notification de commentaires et trackback par mail et messagerie jabber,
  • Pings automatiques vers des sites comme Technorati,
  • Gestion de tags (multicatégories, ou folksonomies),
  • Gestionnaire de pages statiques,
  • Contrôle du SPAM avancé (blacklistes locales et distantes, nombre d'URL dans un commentaire, etc.),
  • Gestion intelligente du cache des pages,
  • Nombreux plugins vers des sites disposant d'API (FlickR, Del.icio.us, Upcomming, LastFM, etc.)
  • Etc.

Bon, le plus simple pour se rendre compte de l'interêt de cet outil, c'est de l'installer et de le tester soi-même.

Tout d'abord, et après avoir installé RoR sur Ubuntu, il faut récupérer les sources Subversion [1] de Typo :

$ cd /path/to/docroot
$ svn checkout svn://leetsoft.com/typo/trunk typo

Ceci fait, il faut créer une base de données MySQL dédiée à Typo :

$ cd typo
$ mysql -u root -p
Enter password:
Welcome to the MySQL monitor.  Commands end with ; or \g.
Your MySQL connection id is 12 to server version: 4.1.12-Debian_1ubuntu3.1-log

Type 'help;' or '\h' for help. Type '\c' to clear the buffer.

mysql> CREATE DATABASE typo_dev;
Query OK, 1 row affected (0.00 sec)

mysql> \q;

On va y insérer le schema SQL fourni :

$ mysql -u root -p typo_dev < db/schema.mysql.sql

Il nous reste à configurer le fameux fichier ./config/database.yml :

login: &login
  adapter: mysql
  host: localhost
  username: <nom_utilisateur_mysql>
  password: <votre_mot_de_passe>

On lance Webrick, le petit serveur web fourni avec RoR :

$ script/server

Et on teste on faisant pointer son navigateur à l'adresse 0.0.0.0:3000.

Bon amusement :)

Notes

[1] Si vous ne disposez pas de Subversion, sudo apt-get install subversion

vendredi 6 janvier 2006

Ruby on Rails #1 - Lets go Ruby !

Je découvre Ruby on Rails (RoR pour les intimes), c'est assez sympa. Pour mémoire, c'est un framework de developpement web rapide basé sur le motif de conception MVC qui offre une facilité de conception, de déploiement ainsi qu'une maintenance aisée, le tout en langage Ruby. J'en veux pour preuve ces quelques vidéos qui m'ont laissées pour le moins scié en quatre, notamment celle-ci.

En plus, ça tourne chez Typhon, mon hébergeur préféré :)

Ce billet est donc le premier d'une série que je rédigerai au gré de mes découvertes de cet outil qui promet d'être passionnant. Commençons par le commencement, l'installation de l'environnement.

Lire la suite...

- page 1 de 2