aboutsummaryrefslogtreecommitdiffstats
path: root/activerecord/lib/active_record/base.rb
diff options
context:
space:
mode:
authorJeremy Kemper <jeremy@bitsweat.net>2006-11-05 21:27:51 +0000
committerJeremy Kemper <jeremy@bitsweat.net>2006-11-05 21:27:51 +0000
commit2fbe0ae7a2d945dbd9d0e0abad23afde75db67fb (patch)
tree9e1af551f499881c5d3fe6b73730e45cf4ad2660 /activerecord/lib/active_record/base.rb
parent5b979ed8ffe5f42747141f632656571f0fd194bf (diff)
downloadrails-2fbe0ae7a2d945dbd9d0e0abad23afde75db67fb.tar.gz
rails-2fbe0ae7a2d945dbd9d0e0abad23afde75db67fb.tar.bz2
rails-2fbe0ae7a2d945dbd9d0e0abad23afde75db67fb.zip
Support nil and Array in :conditions => { attr => value } hashes. Closes #6548.
git-svn-id: http://svn-commit.rubyonrails.org/rails/trunk@5435 5ecf4fe2-1ee6-0310-87b1-e25e094e27de
Diffstat (limited to 'activerecord/lib/active_record/base.rb')
-rwxr-xr-xactiverecord/lib/active_record/base.rb64
1 files changed, 33 insertions, 31 deletions
diff --git a/activerecord/lib/active_record/base.rb b/activerecord/lib/active_record/base.rb
index 3fc9b4bddb..c09cef1118 100755
--- a/activerecord/lib/active_record/base.rb
+++ b/activerecord/lib/active_record/base.rb
@@ -986,7 +986,7 @@ module ActiveRecord #:nodoc:
options.update(:limit => 1) unless options[:include]
find_every(options).first
end
-
+
def find_every(options)
records = scoped?(:find, :include) || options[:include] ?
find_with_associations(options) :
@@ -996,11 +996,11 @@ module ActiveRecord #:nodoc:
records
end
-
+
def find_from_ids(ids, options)
- expects_array = ids.first.kind_of?(Array)
+ expects_array = ids.first.kind_of?(Array)
return ids.first if expects_array && ids.first.empty?
-
+
ids = ids.flatten.compact.uniq
case ids.size
@@ -1192,16 +1192,16 @@ module ActiveRecord #:nodoc:
attribute_names = extract_attribute_names_from_match(match)
super unless all_attributes_exists?(attribute_names)
- conditions = construct_conditions_from_arguments(attribute_names, arguments)
+ attributes = construct_attributes_from_arguments(attribute_names, arguments)
case extra_options = arguments[attribute_names.size]
when nil
- options = { :conditions => conditions }
+ options = { :conditions => attributes }
set_readonly_option!(options)
ActiveSupport::Deprecation.silence { send(finder, options) }
when Hash
- finder_options = extra_options.merge(:conditions => conditions)
+ finder_options = extra_options.merge(:conditions => attributes)
validate_find_options(finder_options)
set_readonly_option!(finder_options)
@@ -1215,7 +1215,7 @@ module ActiveRecord #:nodoc:
else
ActiveSupport::Deprecation.silence do
- send(deprecated_finder, conditions, *arguments[attribute_names.length..-1])
+ send(deprecated_finder, sanitize_sql(attributes), *arguments[attribute_names.length..-1])
end
end
elsif match = /find_or_(initialize|create)_by_([_a-zA-Z]\w*)/.match(method_id.to_s)
@@ -1223,9 +1223,11 @@ module ActiveRecord #:nodoc:
attribute_names = extract_attribute_names_from_match(match)
super unless all_attributes_exists?(attribute_names)
- options = { :conditions => construct_conditions_from_arguments(attribute_names, arguments) }
+ attributes = construct_attributes_from_arguments(attribute_names, arguments)
+ options = { :conditions => attributes }
set_readonly_option!(options)
- find_initial(options) || send(instantiator, construct_attributes_from_arguments(attribute_names, arguments))
+
+ find_initial(options) || send(instantiator, attributes)
else
super
end
@@ -1247,12 +1249,6 @@ module ActiveRecord #:nodoc:
match.captures.last.split('_and_')
end
- def construct_conditions_from_arguments(attribute_names, arguments)
- conditions = []
- attribute_names.each_with_index { |name, idx| conditions << "#{table_name}.#{connection.quote_column_name(name)} #{attribute_condition(arguments[idx])} " }
- [ conditions.join(" AND "), *arguments[0...attribute_names.length] ]
- end
-
def construct_attributes_from_arguments(attribute_names, arguments)
attributes = {}
attribute_names.each_with_index { |name, idx| attributes[name] = arguments[idx] }
@@ -1275,7 +1271,7 @@ module ActiveRecord #:nodoc:
def expand_id_conditions(id_or_conditions)
case id_or_conditions
when Array, Hash then id_or_conditions
- else construct_conditions_from_arguments([primary_key], [id_or_conditions])
+ else sanitize_sql(primary_key => id_or_conditions)
end
end
@@ -1377,26 +1373,32 @@ module ActiveRecord #:nodoc:
klass.base_class.name
end
- #Accepts an array, hash, or string of sql conditions and
- #deals with them accordingly
+ # Accepts an array, hash, or string of sql conditions and sanitizes
+ # them into a valid SQL fragment.
# ["name='%s' and group_id='%s'", "foo'bar", 4] returns "name='foo''bar' and group_id='4'"
# { :name => "foo'bar", :group_id => 4 } returns "name='foo''bar' and group_id='4'"
# "name='foo''bar' and group_id='4'" returns "name='foo''bar' and group_id='4'"
def sanitize_sql(condition)
- return sanitize_sql_array(condition) if condition.is_a?(Array)
- return sanitize_sql_hash(condition) if condition.is_a?(Hash)
- condition
+ case condition
+ when Array; sanitize_sql_array(condition)
+ when Hash; sanitize_sql_hash(condition)
+ else condition
+ end
end
-
- # Accepts a hash of conditions. The hash has each key/value or attribute/value pair
- # sanitized and interpolated into the sql statement.
- # { :name => "foo'bar", :group_id => 4 } returns "name='foo''bar' and group_id= 4"
- def sanitize_sql_hash(hash)
- hash.collect { |attrib, value|
- "#{table_name}.#{connection.quote_column_name(attrib)} = #{quote_value(value)}"
- }.join(" AND ")
+
+ # Sanitizes a hash of attribute/value pairs into SQL conditions.
+ # { :name => "foo'bar", :group_id => 4 }
+ # # => "name='foo''bar' and group_id= 4"
+ # { :status => nil, :group_id => [1,2,3] }
+ # # => "status IS NULL and group_id IN (1,2,3)"
+ def sanitize_sql_hash(attrs)
+ conditions = attrs.map do |attr, value|
+ "#{table_name}.#{connection.quote_column_name(attr)} #{attribute_condition(value)}"
+ end.join(' AND ')
+
+ replace_bind_variables(conditions, attrs.values)
end
-
+
# Accepts an array of conditions. The array has each value
# sanitized and interpolated into the sql statement.
# ["name='%s' and group_id='%s'", "foo'bar", 4] returns "name='foo''bar' and group_id='4'"