Foo is just a test model with a single attribute, name.
Foo.find(:all).map { |e| e.name }
=> [“a”, “b”, “c”, “d”, “e”, “f”, “g”, “h”, “i”]
If you simply add values.flatten! to replace_bind_variables in
activerecord/lib/active_record/base.rb, line 1285
you can do all sorts of nice things like this:
def or_search_with_array(collection, field, *array)
conditions = array.to_a.flatten.map { |c|
" LOWER(#{field}) = ?"
}
collection.find(:all,
:conditions => [ conditions.join(" OR "), array.to_a ])
end
or_search_with_array(Foo, :name, (“a”…“e”).to_a).map { |e| e.name }
=> [“a”, “b”, “c”, “d”, “e”]or_search_with_array(Foo, :name, “b”, “c”, “d”).map { |e| e.name }
=> [“b”, “c”, “d”]or_search_with_array(Foo, :name, [ “a”, “b”, “c” ]).map { |e| e.name }
=> [“a”, “b”, “c”]or_search_with_array(Foo, :name, “c”).map { |e| e.name }
=> [“c”]
My question is, are there any drawbacks to that, any reason why it
isn’t done?
Without it, none of the above works:
or_search_with_array(Foo, :name, [ “a”, “b”, “c” ]).map { |e| e.name }
ActiveRecord::PreparedStatementInvalid: wrong number of bind variables
(1 for 3) in:
LOWER(name) = ? OR LOWER(name) = ? OR LOWER(name) = ?
from …/active_record/base.rb:1311:in
raise_if_bind_arity_mismatch' from .../active_record/base.rb:1285:in
replace_bind_variables’
from …/active_record/base.rb:1276:insanitize_sql' from .../active_record/base.rb:1062:in
add_conditions!’
from …/active_record/base.rb:1012:inconstruct_finder_sql' from .../active_record/base.rb:924:in
find_every’
from …/active_record/base.rb:381:infind' from (irb):5:in
or_search_with_array’
from (irb):9