En regardant en diagonale quelques vidéos de Grafikart sur Ruby on Rails, j’ai noté quelques astuces intéressantes :
rails s -b IP
Pour binder l’IP sur laquelle l’application écoute.
Par exemple, rails s -b 0.0.0.0
permet d’écouter sur toutes les interfaces (utile pour les machines virtuelles)
Callback de modèle
Pour ne pas avoir à ajouter du code dans le contrôleur (après un @objet.save
par exemple).
Son exemple était l’utilisation d’un before_validation
pour setter le slug en fonction du titre d’un article.
Scope avec paramètre
exemple :
scope :online, -> (online) { where(online: online) } |
Scope par défaut
default_scope where(published: true) |
Attention aux effets de bord, notamment si on met un order
dans le defaut_scope
et qu’on veut redéfinir le tri dans le contrôleur !
Pour éviter ces effets de bord, les méthode reorder
, unscoped
et unscope
peuvent être intéressante.
render mon_objet
Si on a un partial du même nom qu’une classe, on peut directement utiliser cette syntaxe.
Exemple : si on boucle sur un tableau d’élément pour les afficher les uns sous les autres, on peut écrire :
@elements.each do |element| render element end |
à partir du moment où on a un fichier partial _element.html.erb
.
On peut même écrire :
render "element", collection: @elements |
ou même :
render @elements |
qui donnera le même résultat. Et ça c’est fort !
content_for
et yield
Penser à les utiliser !
content_for(:title, @element.titre) yield(:title) content_for?(:title) |
exemple :
content_for?(:title) ? yield(:title) : "Mon super titre" |
config.generators
On peut configurer les fichiers qui sont générés quand on fait un rails ...
dans le application.rb
. Par exemple, pour ne pas créer un helper à chaque fois qu’on génère un contrôleur, on peut écrire :
config.generators.helper = false |
Plus d’infos sur guides.rubyonrails.org.
Lancer un serveur en production
rails s -e production |
Attention, il faut du coup une base de données de production.
Supprimer un contrôleur et les fichiers associés
Quand on crée un contrôleur avec la commande rails g controller mon_controleur
, plusieurs fichiers sont générés : le contrôleur, le fichier de test, un fichier SCSS et un fichier JS (ou Coffee).
Pour supprimer ce contrôleur et tous les fichiers associés, on peut utiliser la commande :
rails d controller mon_controleur |
Utiliser un CDN
config.action_controller.asset_host = 'cdn.domain.fr' |
Preview d’email
Quand on génère un mailer avec rails g mailer mon_mailer
, il est généré un fichier mailer dans /app/mailers
, un répertoire de vues dans app/views
, mais aussi un fichier de preview dans test/mailers/preview
.
Dans ce fichier, on crée des méthodes qui appellent celles du fichier mailer. Par exemple, si notre fichier mailer contient un méthode contact(prenom), on peut définir une méthode contact dans notre fichier preview :
ContactMailer.contact("Toto") |
Ensuite, on peut accéder au preview via l’url rails/mailers/contact_mailer
qui liste toutes les méthodes de preview.
Associations
.includes
Exemple : on affiche un tableau d’articles avec pour chaque article sa catégorie. Pour cela, dans le contrôleur on aurait écrit :
@articles = Article.all |
Et dans la vue, quelque chose comme :
<%= article.categorie.titre %> |
Cela n’est pourtant pas très efficace : on a une requête qui récupère les articles :
SELECT * FROM articles |
et pour chaque article, une requête qui va chercher sa catégorie :
SELECT * FROM categorie WHERE id = 2 LIMIT 1 |
Soit n+1 requêtes (où n correspond aux nombres d’articles).
Pour contrer cela, on peut faire dans le contrôleur :
@articles = Article.includes(:categorie).all |
Ce qui donnera, au niveau des requêtes :
SELECT * FROM articles SELECT * FROM categories WHERE id IN (2,3) |
On peut même faire :
@articles = Categorie.includes(articles: :tags).all |
Pour récupérer toutes les catégories et les articles associés ainsi que les tags associés aux articles.
:dependent
Pour supprimer tous les articles associés à une catégorie à la suppression de la catégorie, on peut écrire :
class Categorie < ApplicationRecord has_many :articles, dependent: :destroy end |
qui supprimera les objets articles associés (et appellera donc les callbacks)
ou :
class Categorie < ApplicationRecord has_many :articles, dependent: :delete_all end |
qui supprimera directement les articles associés en base de données (et n’appellera pas les callbacks)
:counter_cache
Pour afficher le nombre d’associations sans faire de requête supplémentaire, on peut utiliser un « counter_cache » :
class Article < ApplicationRecord belongs_to :categorie, counter_cache: true end |
Il faut pour cela ajouter un champ posts_count dans la table catégorie (avec 0 comme valeur par défaut).
La valeur de posts_count sera mis à jour automatiquement quand on ajoute ou supprime un article à une catégorie.
has_and_belongs_to_many
Pour créer une table de liaison, on peut faire la migration :
rails g migration create_join_table_articles_tags article tag |
et utiliser le has_and_belongs_to_many
class Article < ApplicationRecord has_and_belongs_to_many :tags end class Tag < ApplicationRecord has_and_belongs_to_many :articles end |
L’association has_many: :through permet de faire la même chose avec une classe de liaison. Cela peut être utile lorsqu’on veut stocker des choses dans la table d’association.
article.tags.delete(tag)
supprime la liaison
article.tags.destroy(tag)
supprime le tag et les liaisons
Très bon article, j’avais commencé à regarder les épisodes et ça me fait un bon résumé 🙂
Merci pour ton commentaire ! N’hésite pas à regarder les vidéos, mon article n’étant pas un résumé : j’ai simplement noté les astuces que je ne connaissais pas et qui me semblaient intéressantes.
hello 🙂
j’aime bien aussi ce genre de tips sur les best pratices 🙂
c’est toujours bon à prendre
si je peux me permettre, de mon coté je réalise des formations ruby et rails plutôt axées business https://rubyrails.ninja/formations si vous voulez jeter un oeil au contenu