homeASCIIcasts

15: Giocare con le condizioni della find 

(view original Railscast)

Other translations: En Es Fr

Other formats:

Written by Andrea Salicetti

Questo episodio affronta le condizioni del metodo find. Di sotto sono riportate alcune linee dalla script/console, che mostrano l’ SQL che è prodotto da questi comandi.

Task.find(:all, :conditions => ["completed = ? AND priority = ?", false, 2])
SELECT * FROM "tasks" WHERE (completed = 'f' AND priority = 2)

Trova tutti i task incompleti che hanno prorità pari a 2.

L’esempio di sopra funziona, ma come faremmo a recuperare tutti i Tasks che hanno una priority che vale nil?

Task.find(:all, :conditions => ["completed = ? AND priority = ?", false, nil])
SELECT * FROM "tasks" WHERE (completed = 'f' AND priority = NULL) 

La ricerca per valori null produce SQL scorretto.

L’SQL prodotto sopra non è corretto. Per recuperare valori null, la corretta sintassi sarebbe infatti priority IS NULL, non priority = NULL. Analogamente, se volessimo recuperare i record passando più di un valore per il campo priority, usando un array o un range, dovremmo cambiare lo statement di find per usare correttamente IN al posto di =, e mettere le parentesi a contorno del secondo punto di domanda, al fine di garantire che l’SQL prodotto sia sintatticamente corretto.

Task.find(:all, :conditions => ["completed = ? AND priority IN (?)", false, [1,3]])
SELECT * FROM "tasks" WHERE (completed = 'f' AND priority IN (1,3))

A partire da Rails 1.2, c’è un modo miglior per passare le condizioni: mediante un hash. Usare un hash di condizioni garantisce che Rails adotti le condizioni appropriate quando esegue le query sul database.

Task.find(:all, :conditions => { :completed => false, :priority => [1,3] }
SELECT * FROM "tasks" WHERE (completed = 'f' AND priority IN (1,3)

Uso di un hash di condizioni con un parametro array.

Task.find(:all, :conditions => {:completed => false, :priority => 2..4})
SELECT * FROM "tasks" WHERE ("tasks"."priority" BETWEEN 2 AND 4 AND "tasks"."completed" = 'f') 

Se si passa un range, questo viene tradotto con la clausola BETWEEN nell’SQL.

Utilizzo con find dinamiche

Nell’episodio 2 abbiamo usato metodi find_by dinamici. Anche questi possono accettare valori nil, array o range come argomenti.

Task.find_by_priority(1..5)
SELECT * FROM "tasks" WHERE ("tasks"."priority" BETWEEN 1 AND 5) LIMIT 1

L’utilizzo di hash nelle condizioni di find assicura che Rails generi l’SQL corretto al passaggio di un qualsiasi tipo di parametro alla find.