2009-07-23 10 views
5

Ho un'azione indice in rotaie in grado di gestire un bel po 'params esempio:dinamica trovare condizioni di record attivo

params[:first_name] # can be nil or first_name 
params[:age]  # can be nil or age 
params[:country] # can be nil or country 

Quando trovare gli utenti che vorrei e di tutte le condizioni che non sono pari a zero. Questo mi dà 8 permutazioni delle condizioni di ricerca.

Come posso mantenere il mio codice ASCIUTTO e flessibile e non finire con un mucchio di istruzioni if solo per costruire le condizioni per il ritrovamento. Tenete a mente che se non sono specificate le condizioni Voglio solo tornare User.all

risposta

1

Questo sembra funzionare abbastanza bene:

conditions = params.slice(:first_name, :age, :country) 
hash = conditions.empty? ? {} : {:conditions => conditions} 
@users = User.all hash 
3

ne dite qualcosa di simile:

conditions = params.only(:first_name, :age, :country) 
conditions = conditions.delete_if {|key, value| value.blank?} 

if conditions.empty? 
    User.all 
else 
    User.all(:conditions => conditions) 
end 
+0

Stranamente il mio hash params non sembra avere un solo metodo –

0

Si potrebbe provare Ambition, o un numero di altre estensioni ActiveRecord.

3

Io normalmente utilizzare gli ambiti di nome per qualcosa di simile:

class User < ActiveRecord::Base 
    named_scope :name_like, lambda {|name| {:conditions => ["first_name LIKE ?", "#{name}%"]}} 
    named_scope :age, lambda {|age| {:conditions => {:age => age}}} 
    named_scope :in_country, lambda {|country| {:conditions => {:country => country}}} 
end 

class UsersController < ActionController 
    def index 
    root = User 
    root = root.name_like(params[:first_name]) unless params[:first_name].blank? 
    root = root.age(params[:age]) unless params[:age].blank? 
    root = root.country(params[:country]) unless params[:age].blank? 

    @users = root.paginate(params[:page], :order => "first_name") 
    end 
end 

Questo è quello che faccio di solito.

0

Questo funziona anche per me

conditions = params[:search] ? params[:search].keep_if{|key, value| !value.blank?} : {} 
User.all(:conditions => conditions) 
1

Utilizzando James Healy risposta, modifico il codice da utilizzare in Rails 3.2 (nel caso in cui qualcuno là fuori bisogno di questo).

conditions = params.slice(:first_name, :age, :country) 
conditions = conditions.delete_if {|key, value| value.blank?} 

@users = User.where(conditions) 
0

Se vi capita di essere su un antico progetto (Rails 2.x) e molto disordinato, si potrebbe fare qualcosa di simile a quanto segue per l'aggiunta di nuovi campi alla query originale.

Codice originale:

User.find(:all, 
    :conditions => ['first_name LIKE ? AND age=? AND country=?', 
     "#{name}%", age, country] 

Aggiunta di una nuova condizione dinamica zip_code campo:

zip_code = params[:zip_code] # Can be blank 
zip_query = "AND zip_code = ?" unless zip_code.blank? 

User.find(:all, 
    :conditions => ['first_name LIKE ? AND age=? AND country=? #{zip_query}', 
     "#{name}%", age, country, zip_code].reject(&:blank?) 

Aggiunta di un reject(&:blank?) al conditions array filtrerà il valore nil.

Nota: Le altre risposte sono molto meglio se si sta codificando da zero o refactoring.

Problemi correlati