2010-10-18 5 views
1

Dans Rails 3, j'ai créé un formulaire de recherche qui effectue une recherche avec des conditions dans le fichier Modèles.Rails faire un TROUVER avec des conditions?

@projects = find(:all, 
       :select => 'projects.*', 
       :conditions => ['name = ?', search_name] 
       ).first 

Cela fonctionne très bien si un nom est fourni dans le formulaire de recherche (nom_recherche). Le problème est si search_name est vide, Rails Errors (je ne peux pas dire que je le blâme) ...

Quelle est la façon intelligente de gérer cette situation? Je voudrais, si search_name est vide, ne pas erreur mais retourner tout.

Suggestions? Merci!

Répondre

5

Vous pouvez créer une étendue pour gérer cela. Dans votre modèle de projet, ajouter quelque chose comme:

scope :search_by(name), lambda{|name| first.where(:name => name) unless name.blank?} 

puis dans votre contrôleur, appelez simplement:

Project.search_by(params[:search]) 

EDIT:

Si vous devez serach pour plusieurs champs que vous pouvez adapter la portée :

portée: search_by (nom), lambda {| nom | first.includes (: owner) .where ("projects.name LIKE? OU propriétaires.name LIKE?", nom, name) sauf name.blank?}

+0

Très élégant. Quelle est la recherche de mon projet est par plusieurs champs comme (propriétaire, nom, date de création) et seulement le nom est facultatif? – AnApprentice

+0

ne devrait-il pas être "scope: search_by (nom), lambda {| nom | first.where (: nom => nom) à moins que name.blank?}"? – ipsum

+0

Votre juste ipsum ... corrigé! – Yannis

3
if search_name.blank? 
    @projects = Project.order(:name) 
else 
    @projects = Project.where(:name => search_name) 
end 
+0

J'ai considéré cela mais j'ai pensé qu'il y avait peut-être une solution de type Rails plus propre ? – AnApprentice

+0

'@projects = (nom_recherche.blank? Project.order (: nom): Project.where (: nom => nom_recherche))' :) –

+0

Je dirais que l'utilisation de ternary ici est assez moche, mais si vous voulez un - doublure, vas-y. – bensie

1

La façon la plus propre est en utilisant le chargement paresseux avec les nouvelles fonctionnalités ActiveRecord comme celui-ci:

@projects = Project.order (: nom) @projects = @ projects.where (: name => SEARCH_NAME) if search_name

Vous pouvez ajouter autant de conditions que vous le souhaitez. Ils ne seront pas exécutés tant que vous n'avez pas besoin des résultats (avec @ projects.all ou @ projects.each, etc ...)

+0

Le chargement paresseux est idéal, mais dans ce cas, il effectuera également le ORDER BY sur la colonne name, ce qui peut ne pas être souhaitable dans la recherche. Très nouveau dans Rails master, ils ont ajouté la méthode except(), qui pourrait être utilisée pour .except (: order) ... – bensie

Questions connexes