Imaginez par exemple que vous vouliez une interface de gestion de nos étudiants précédemment crées.
Si nos souhaits se limitent à l'ajout, modification, suppression, le scaffold de Rails ferait l'affaire, mais on va ici partir "from scratch" pour vous montrer à quel point tout ceci est aisé.

On créera alors un Controller StudentsController

script/generate controller Students

Rails2.1 permet de faire très facilement des controllers dit "Restful".

Si vous ne savez pas ce dont il s'agit je vous invite à lire l'excellente traduction de Biologeek d'un article de Softies on Rails :
Pour ne plus être en REST, comprendre cette architecture
et/ou celle-ci de pompage.net :
Comment j'ai expliqué REST à ma femme

Si vous avez lu et compris, vous aurez retenu qu'avec REST on utilise tous les verbes du protocole HTTP et qu'on parle de ressources plutôt que de pages web ou d'images...

Les ressources, dans notre cas, ce sont des étudiants et voici quelques URLs qui vont nous intéresser

GET    /students                        :action=>"index"
POST   /students                        :action=>"create"
GET    /students/new                    :action=>"new"
GET    /students/:id/edit               :action=>"edit"
GET    /students/:id                    :action=>"show"
PUT    /students/:id                    :action=>"update"
DELETE /students/:id                    :action=>"destroy"

Vous aurez compris que pour afficher un utilisateur on fera /students/:id, mais et c'est là où REST intervient, on utilisera la même adresse pour le supprimer et le modifier.

En effet une ressource = une URI, donc un utilisateur => "/students/:id"

Par contre, le type de requête HTTP, respectivement GET, DELETE ET PUT nous informera sur ce que l'on souhaite faire.

Avec Rails, les actions appelées sont les méthodes publiques des controllers, écrivons donc la méthode qui va afficher un utilisateur

def show
  @student = Student.find(params[:id])
end

Et voilà...
Quoi c'est tout :D

Oui, pour l'instant cela peut suffire, en effet Rails a récupéré notre ressource (l'utilisateur désiré) grâce au find et par défaut, il va appeler la méthode render avec la vue correspondante (show) dans le dossier des vues.

Cette dernière aura accès aux variables d'instance de notre classe et donc à l'objet @student et toutes ses propriétés.

Essayons maintenant d'écrire la méthode nécessaire à la modification (update) d'un utilisateur.

def update
  @student = Student.find(params[:id])
  @student.update_attributes(params[:student])
  redirect_to @student
end

Dans la première ligne, je récupère l'étudiant à créer.
Dans la seconde j'update ses attributs (donc propriétés) avec les paramètres passés par le formulaire.
Dans la dernière je redirige l'utilisateur vers le student modifié (cela appellera la méthode show précédemment créée)

En réalité il faudrait gérer le fait que la sauvegarde se soit ou non bien passée, cela donnerait donc :

def update
  @student = Student.find(params[:id])
    if @student.update_attributes(params[:student])
      redirect_to(@student)
    else
      render :action => "edit"
    end
end

C'est presque la même chose sauf que si la sauvegarde n'a pas fonctionné, on revient sur la page d'édition.

Voilà pour la version HTML, mais si vous avez compris REST, vous savez que l'on aimerait pouvoir avoir d'autre représentation de notre ressource qu'une page web !
Pourquoi pas par exemple, une représentation XML que l'on pourrait passer à un webservice distant ou je ne sais quel autre usage.

Ré-écrivons notre méthode show dans ce but

def show
  @student = Student.find(params[:id])

  respond_to do |format|
    format.html # show.html.erb
    format.xml  { render :xml => @student }
  end
end

Et voilà, notre controller répondra désormais à la demande générée.
Si vous lui demandez du HTML, celui là réagira comme précédemment, si vous le voulez en XML, il exécutera la ligne :

format.xml  { render :xml => @student }

et renverra donc notre objet student converti en XML.

Vous voulez discuter avec une application Flash/Flex/AIR..., installez RubyAMF (l'équivalent Ruby de AMFPHP) et il vous suffira de rajouter :

format.amf { render :amf => @student }

Et voilà vous avez côté ActionScript votre objet tout chaud sans nécessité de désérialisation.
Et vous n'avez presque rien eu à faire côté Rails et finalement, c'est normal, la logique et la ressource sont les mêmes, seul le rendu change !

Comme vous pouvez le voir, ActionController se débrouille donc très bien pour faire la circulation entre la vue et les modèles.

carrefour

Une des rares autres tâches qui incombe au controller est le contrôle des accès, si vous souhaitez vérifier que l'utilisateur connecté peut accéder à telle ou telle ressource, c'est à lui de s'en charger.

Imaginons dans notre exemple, que les étudiants puissent consulter les informations les concernant, mais que seul l'intendance puisse les éditer, ajouter, supprimer.

Ajoutons à notre controller la ligne suivante :

before_filter :authenticate , :exept => [:index, :show]

Cela signifie qu'avant toutes les méthodes sauf index et show, on exécutera la méthode authenticate et que l'on ne fera la suite que si cette méthode renvoi true.

On peut donc rajouter à la fin de notre controller la méthode authenticate :

private

def authenticate
  authenticate_or_request_with_http_basic do |username, password|
    username == "foo" && password == "bar"
  end
end

On notera que la méthode a été placée après le mot clé private afin de signifier que celle-ci n'est pas une action exécutable par le navigateur.

Notre action va ouvrir une boite de dialogue (si l'utilisateur n'est pas encore authentifier) nous demandant notre login et mot de passe et renverra true si et seulement si ceux-ci sont "foo" et "bar"
N.B. : Evidement, en réalité, cette vérification s'effectuerait en base de donnée :)

Et voilà, désormais seul les personnes connaissant les logins et mot de passe ont accès à l'intégralité de l'application.

Ce sera tout pour ce soir, nous avons désormais vu comment écrire du Ruby, puis, comment fonctionnent les parties Model et Controller de Rails.

Il ne nous reste donc plus qu'une partie à aborder : les vues.
A bientôt pour ce dernier chapitre.