diff options
Diffstat (limited to 'activerecord/lib/active_record/type')
4 files changed, 46 insertions, 6 deletions
diff --git a/activerecord/lib/active_record/type/big_integer.rb b/activerecord/lib/active_record/type/big_integer.rb new file mode 100644 index 0000000000..0c72d8914f --- /dev/null +++ b/activerecord/lib/active_record/type/big_integer.rb @@ -0,0 +1,13 @@ +require 'active_record/type/integer' + +module ActiveRecord + module Type + class BigInteger < Integer # :nodoc: + private + + def max_value + ::Float::INFINITY + end + end + end +end diff --git a/activerecord/lib/active_record/type/boolean.rb b/activerecord/lib/active_record/type/boolean.rb index 1311be3944..978d16d524 100644 --- a/activerecord/lib/active_record/type/boolean.rb +++ b/activerecord/lib/active_record/type/boolean.rb @@ -14,9 +14,13 @@ module ActiveRecord true else if !ConnectionAdapters::Column::FALSE_VALUES.include?(value) - ActiveSupport::Deprecation.warn(<<-EOM) - You attempted to assign a value which is not explicitly true or false to a boolean column. Currently this value casts to false. This will change to match Ruby's sematics, and will cast to true in Rails 5.0. If you would like to maintain the current behavior, you should explicitly handle the values you would like cast to false. - EOM + ActiveSupport::Deprecation.warn(<<-MSG.squish) + You attempted to assign a value which is not explicitly `true` or `false` + to a boolean column. Currently this value casts to `false`. This will + change to match Ruby's semantics, and will cast to `true` in Rails 5. + If you would like to maintain the current behavior, you should + explicitly handle the values you would like cast to `false`. + MSG end false end diff --git a/activerecord/lib/active_record/type/decimal_without_scale.rb b/activerecord/lib/active_record/type/decimal_without_scale.rb index cabdcecdd7..ff5559e300 100644 --- a/activerecord/lib/active_record/type/decimal_without_scale.rb +++ b/activerecord/lib/active_record/type/decimal_without_scale.rb @@ -1,8 +1,8 @@ -require 'active_record/type/integer' +require 'active_record/type/big_integer' module ActiveRecord module Type - class DecimalWithoutScale < Integer # :nodoc: + class DecimalWithoutScale < BigInteger # :nodoc: def type :decimal end diff --git a/activerecord/lib/active_record/type/integer.rb b/activerecord/lib/active_record/type/integer.rb index 08477d1303..d69e5b3f28 100644 --- a/activerecord/lib/active_record/type/integer.rb +++ b/activerecord/lib/active_record/type/integer.rb @@ -3,21 +3,44 @@ module ActiveRecord class Integer < Value # :nodoc: include Numeric + def initialize(*) + super + @range = -max_value...max_value + end + def type :integer end alias type_cast_for_database type_cast + protected + + attr_reader :range + private def cast_value(value) case value when true then 1 when false then 0 - else value.to_i rescue nil + else + result = value.to_i rescue nil + ensure_in_range(result) if result + result end end + + def ensure_in_range(value) + unless range.cover?(value) + raise RangeError, "#{value} is too large for #{self.class} with limit #{limit || 4}" + end + end + + def max_value + limit = self.limit || 4 + 1 << (limit * 8 - 1) # 8 bits per byte with one bit for sign + end end end end |