RangeError for simple integer assignment in Rails 4.2.0 that should be caught by validation
Asked Answered
W

4

12

* UPDATE: this is now fixed in 4.2.stable and 4.2.1 *

in Rails 4.2.0 (and current 4.2.stable), the ensure_in_range method happens before AR validation, yielding a RangeError

if I do something as simple as

@obj.threshold = 10_000_000_000

on a column with a postgres type integer

 threshold  | integer                     | 

it yields

RangeError: 10000000000 is out of range for ActiveRecord::ConnectionAdapters::PostgreSQL::OID::Integer with limit 4 from .../2.0.0-p598/lib/ruby/gems/2.0.0/bundler/gems/rails-62e9e61f2d1b/activerecord/lib/active_record/type/integer.rb:41:in `ensure_in_range'

which is true! but tell that to the users. there's an ActiveRecord model validation like

  validates :threshold,  presence: true,
    numericality: { greater_than_or_equal_to: 0, less_than: 1_000_000}

i can't imagine this is expected behavior, anyone have any explanation why this type cast happens before validation?

Withdrew answered 22/1, 2015 at 17:56 Comment(3)
I'm encountering the same issue. Haven't figured out why this is happening.Hedelman
The issue is caused by ActiveRecord's built-in typecasting, which is invoked in attribute setters (as you've discovered). Don't know of a way around it off the top of my head, but I'll give it some thought.Hemminger
In time of writing this comment only update to rails 4.2.1 solves this issue, in 4.2.0 I still get RangeError.Thorvaldsen
D
5

Get the latest rails version to fix this error, it was recently fixed by Sean Griffin

To do that before a version comes out, remove the specific version in your gemfile and use the git location hint :

gem 'rails', :git => 'https://github.com/rails/rails.git'
Drip answered 23/1, 2015 at 22:52 Comment(3)
awesome. thanks for the heads up. i was going take more drastic measures on monday. ;)Withdrew
Is there a workaround for this, as I keep getting Could not find gem 'arel (= 7.0.0.alpha) ruby', which is required by gem 'rails (>= 0) ruby', in any of the sources. when trying bundle install with that line.Fairleigh
@Fairleigh github.com/rails/rails/issues/19624. Add this to your Gemfile: gem 'arel', github: 'rails/arel'Potherb
P
2

You can force your migration file to use a BigInt. I had the same problem but I am not using Rails but just ActiveRecord. This will solve your bug:

t.integer :really_big_int, limit: 8

Plowshare answered 4/12, 2015 at 10:18 Comment(0)
C
0

If you have a single validation, then upgrading to Rails 4.2.1 does the trick. However, if you've got multiple validations, such as also validating uniqueness, you have to upgrade to a more recent version than 4.2.1. I upgraded to 4.2.3. I don't know whether 4.2.2 works or not.

Cockeyed answered 14/8, 2015 at 1:35 Comment(2)
In 4.2.3, 4.2.4 doesn't work either: <maxint> is out of range for ActiveRecord::ConnectionAdapters::PostgreSQL::OID::Integer with limit 4Supercilious
I limited my "myint" based on Sean Griffin gem mentioned before to make it work.Supercilious
S
0

In my case this also happens on simple where(some_id: BIG_NUMBER_HERE). I wouldn't describe it as expected, this should rather result in ActiveRecord::RecordNotFound

Skye answered 20/8, 2015 at 9:56 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.