aboutsummaryrefslogtreecommitdiffstats
path: root/activerecord
diff options
context:
space:
mode:
authorTheMonster <alwahsh.ahmed@gmail.com>2014-02-26 03:24:44 +0200
committerTheMonster <alwahsh.ahmed@gmail.com>2014-02-27 23:54:49 +0200
commit6e53d92498ada27cea6c7bae85708fcf5579223c (patch)
treed2f95b5c979111c68c738a102d0ff610a4f7ea32 /activerecord
parent14e697cf2a1f2a4d223463839f6748fca4658bcf (diff)
downloadrails-6e53d92498ada27cea6c7bae85708fcf5579223c.tar.gz
rails-6e53d92498ada27cea6c7bae85708fcf5579223c.tar.bz2
rails-6e53d92498ada27cea6c7bae85708fcf5579223c.zip
Fix a bug affecting validations of enum attributes
This fixes a bug where any enum attribute of a model would be evaluated always as 0 when calling the database on validations. This fix converts the value of the enum attribute to its integer value rather than the string before building the relation as the bug occured when the string finally gets converted to integer using string.to_i which converts it to 0. [Vilius Luneckas, Ahmed AbouElhamayed]
Diffstat (limited to 'activerecord')
-rw-r--r--activerecord/CHANGELOG.md8
-rw-r--r--activerecord/lib/active_record/validations/uniqueness.rb7
-rw-r--r--activerecord/test/cases/enum_test.rb27
3 files changed, 42 insertions, 0 deletions
diff --git a/activerecord/CHANGELOG.md b/activerecord/CHANGELOG.md
index 58f680a03f..2845e945db 100644
--- a/activerecord/CHANGELOG.md
+++ b/activerecord/CHANGELOG.md
@@ -1,3 +1,11 @@
+* Fixed error with validation with enum fields for records where the
+ value for any enum attribute is always evaluated as 0 during
+ uniqueness validation.
+
+ Fixes #14172
+
+ *Vilius Luneckas* *Ahmed AbouElhamayed*
+
* `before_add` callbacks are fired before the record is saved on
`has_and_belongs_to_many` assocations *and* on `has_many :through`
associations. Before this change, `before_add` callbacks would be fired
diff --git a/activerecord/lib/active_record/validations/uniqueness.rb b/activerecord/lib/active_record/validations/uniqueness.rb
index 7ebe9dfec0..49b0f73219 100644
--- a/activerecord/lib/active_record/validations/uniqueness.rb
+++ b/activerecord/lib/active_record/validations/uniqueness.rb
@@ -13,6 +13,7 @@ module ActiveRecord
def validate_each(record, attribute, value)
finder_class = find_finder_class_for(record)
table = finder_class.arel_table
+ value = map_enum_attribute(finder_class,attribute,value)
value = deserialize_attribute(record, attribute, value)
relation = build_relation(finder_class, table, attribute, value)
@@ -91,6 +92,12 @@ module ActiveRecord
value = coder.dump value if value && coder
value
end
+
+ def map_enum_attribute(klass,attribute,value)
+ mapping = klass.enum_mapping_for(attribute.to_s)
+ value = mapping[value] if value && mapping
+ value
+ end
end
module ClassMethods
diff --git a/activerecord/test/cases/enum_test.rb b/activerecord/test/cases/enum_test.rb
index 1b95708cb3..f8ebd7caee 100644
--- a/activerecord/test/cases/enum_test.rb
+++ b/activerecord/test/cases/enum_test.rb
@@ -222,4 +222,31 @@ class EnumTest < ActiveRecord::TestCase
end
end
end
+
+ test "validate uniqueness" do
+ klass = Class.new(ActiveRecord::Base) do
+ def self.name; 'Book'; end
+ enum status: [:proposed, :written]
+ validates_uniqueness_of :status
+ end
+ klass.delete_all
+ klass.create!(status: "proposed")
+ book = klass.new(status: "written")
+ assert book.valid?
+ book.status = "proposed"
+ assert_not book.valid?
+ end
+
+ test "validate inclusion of value in array" do
+ klass = Class.new(ActiveRecord::Base) do
+ def self.name; 'Book'; end
+ enum status: [:proposed, :written]
+ validates_inclusion_of :status, in: ["written"]
+ end
+ klass.delete_all
+ invalid_book = klass.new(status: "proposed")
+ assert_not invalid_book.valid?
+ valid_book = klass.new(status: "written")
+ assert valid_book.valid?
+ end
end