Stop handling AR RangeError when assign a attribute

Active Record 4.2.1 and upper no more raises a `RangeError` on the
assign, only at database level [1].

This will remove all code related to handling of Active Record `RangeError`.

Also, this upgrades the internal dependency on Rails 4.2 to 4.2.3.

[1]: fed7d7cd7c
This commit is contained in:
Mauro George 2015-07-23 19:19:47 -03:00 committed by Elliot Winkler
parent 9268b4940f
commit 73cf275d10
8 changed files with 87 additions and 300 deletions

View File

@ -1,6 +1,6 @@
GIT
remote: git://github.com/pry/pry.git
revision: f0cbec507111743fdbc273735ea4f0f6164a5b21
revision: 83d000b76a4ca88277ab8aa3d4e71ae84c965d0d
specs:
pry (0.10.1)
coderay (~> 1.1.0)
@ -10,76 +10,74 @@ GIT
GEM
remote: https://rubygems.org/
specs:
actionmailer (4.2.0)
actionpack (= 4.2.0)
actionview (= 4.2.0)
activejob (= 4.2.0)
actionmailer (4.2.3)
actionpack (= 4.2.3)
actionview (= 4.2.3)
activejob (= 4.2.3)
mail (~> 2.5, >= 2.5.4)
rails-dom-testing (~> 1.0, >= 1.0.5)
actionpack (4.2.0)
actionview (= 4.2.0)
activesupport (= 4.2.0)
rack (~> 1.6.0)
actionpack (4.2.3)
actionview (= 4.2.3)
activesupport (= 4.2.3)
rack (~> 1.6)
rack-test (~> 0.6.2)
rails-dom-testing (~> 1.0, >= 1.0.5)
rails-html-sanitizer (~> 1.0, >= 1.0.1)
actionview (4.2.0)
activesupport (= 4.2.0)
rails-html-sanitizer (~> 1.0, >= 1.0.2)
actionview (4.2.3)
activesupport (= 4.2.3)
builder (~> 3.1)
erubis (~> 2.7.0)
rails-dom-testing (~> 1.0, >= 1.0.5)
rails-html-sanitizer (~> 1.0, >= 1.0.1)
activejob (4.2.0)
activesupport (= 4.2.0)
rails-html-sanitizer (~> 1.0, >= 1.0.2)
activejob (4.2.3)
activesupport (= 4.2.3)
globalid (>= 0.3.0)
activemodel (4.2.0)
activesupport (= 4.2.0)
activemodel (4.2.3)
activesupport (= 4.2.3)
builder (~> 3.1)
activerecord (4.2.0)
activemodel (= 4.2.0)
activesupport (= 4.2.0)
activerecord (4.2.3)
activemodel (= 4.2.3)
activesupport (= 4.2.3)
arel (~> 6.0)
activeresource (4.0.0)
activemodel (~> 4.0)
activesupport (~> 4.0)
rails-observers (~> 0.1.1)
activesupport (4.2.0)
activesupport (4.2.3)
i18n (~> 0.7)
json (~> 1.7, >= 1.7.7)
minitest (~> 5.1)
thread_safe (~> 0.3, >= 0.3.4)
tzinfo (~> 1.1)
ansi (1.5.0)
appraisal (1.0.2)
appraisal (1.0.3)
bundler
rake
thor (>= 0.14.0)
arel (6.0.0)
arel (6.0.2)
bcrypt (3.1.10)
builder (3.2.2)
byebug (4.0.4)
byebug (5.0.0)
columnize (= 0.9.0)
celluloid (0.16.0)
timers (~> 4.0.0)
coderay (1.1.0)
coffee-rails (4.1.0)
coffee-script (>= 2.2.0)
railties (>= 4.0.0, < 5.0)
coffee-script (2.3.0)
coffee-script (2.4.1)
coffee-script-source
execjs
coffee-script-source (1.9.0)
coffee-script-source (1.9.1.1)
columnize (0.9.0)
diff-lcs (1.2.5)
erubis (2.7.0)
execjs (2.3.0)
ffi (1.9.8)
execjs (2.5.2)
ffi (1.9.10)
formatador (0.2.5)
globalid (0.3.0)
globalid (0.3.5)
activesupport (>= 4.1.0)
guard (2.12.5)
guard (2.12.9)
formatador (>= 0.2.4)
listen (~> 2.7)
listen (>= 2.7, <= 4.0)
lumberjack (~> 1.0)
nenv (~> 0.1)
notiffany (~> 0.0)
@ -89,108 +87,105 @@ GEM
guard-yard (2.1.4)
guard (>= 1.1.0)
yard (>= 0.7.0)
hike (1.2.3)
hitimes (1.2.2)
i18n (0.7.0)
jbuilder (2.2.6)
jbuilder (2.3.1)
activesupport (>= 3.0.0, < 5)
multi_json (~> 1.2)
jquery-rails (4.0.3)
jquery-rails (4.0.4)
rails-dom-testing (~> 1.0)
railties (>= 4.2.0)
thor (>= 0.14, < 2.0)
json (1.8.2)
listen (2.10.0)
celluloid (~> 0.16.0)
json (1.8.3)
listen (3.0.3)
rb-fsevent (>= 0.9.3)
rb-inotify (>= 0.9)
loofah (2.0.1)
loofah (2.0.2)
nokogiri (>= 1.5.9)
lumberjack (1.0.9)
mail (2.6.3)
mime-types (>= 1.16, < 3)
method_source (0.8.2)
mime-types (2.4.3)
mime-types (2.6.1)
mini_portile (0.6.2)
minitest (5.5.1)
minitest-reporters (1.0.10)
minitest (5.7.0)
minitest-reporters (1.0.19)
ansi
builder
minitest (>= 5.0)
ruby-progressbar
multi_json (1.10.1)
multi_json (1.11.2)
nenv (0.2.0)
nokogiri (1.6.6.2)
mini_portile (~> 0.6.0)
notiffany (0.0.6)
nenv (~> 0.1)
shellany (~> 0.0)
pg (0.18.1)
posix-spawn (0.3.9)
protected_attributes (1.0.8)
pg (0.18.2)
posix-spawn (0.3.11)
protected_attributes (1.0.9)
activemodel (>= 4.0.1, < 5.0)
pry-byebug (3.1.0)
byebug (~> 4.0)
pry-byebug (3.2.0)
byebug (~> 5.0)
pry (~> 0.10)
pygments.rb (0.6.2)
pygments.rb (0.6.3)
posix-spawn (~> 0.3.6)
yajl-ruby (~> 1.2.0)
rack (1.6.0)
rack (1.6.4)
rack-test (0.6.3)
rack (>= 1.0)
rails (4.2.0)
actionmailer (= 4.2.0)
actionpack (= 4.2.0)
actionview (= 4.2.0)
activejob (= 4.2.0)
activemodel (= 4.2.0)
activerecord (= 4.2.0)
activesupport (= 4.2.0)
rails (4.2.3)
actionmailer (= 4.2.3)
actionpack (= 4.2.3)
actionview (= 4.2.3)
activejob (= 4.2.3)
activemodel (= 4.2.3)
activerecord (= 4.2.3)
activesupport (= 4.2.3)
bundler (>= 1.3.0, < 2.0)
railties (= 4.2.0)
railties (= 4.2.3)
sprockets-rails
rails-deprecated_sanitizer (1.0.3)
activesupport (>= 4.2.0.alpha)
rails-dom-testing (1.0.5)
rails-dom-testing (1.0.6)
activesupport (>= 4.2.0.beta, < 5.0)
nokogiri (~> 1.6.0)
rails-deprecated_sanitizer (>= 1.0.1)
rails-html-sanitizer (1.0.1)
rails-html-sanitizer (1.0.2)
loofah (~> 2.0)
rails-observers (0.1.2)
activemodel (~> 4.0)
railties (4.2.0)
actionpack (= 4.2.0)
activesupport (= 4.2.0)
railties (4.2.3)
actionpack (= 4.2.3)
activesupport (= 4.2.3)
rake (>= 0.8.7)
thor (>= 0.18.1, < 2.0)
rake (10.4.2)
rb-fsevent (0.9.4)
rb-fsevent (0.9.5)
rb-inotify (0.9.5)
ffi (>= 0.5.0)
rdoc (4.2.0)
json (~> 1.4)
redcarpet (3.2.2)
rspec-core (3.2.0)
rspec-support (~> 3.2.0)
rspec-expectations (3.2.0)
redcarpet (3.3.2)
rspec-core (3.3.2)
rspec-support (~> 3.3.0)
rspec-expectations (3.3.1)
diff-lcs (>= 1.2.0, < 2.0)
rspec-support (~> 3.2.0)
rspec-mocks (3.2.0)
rspec-support (~> 3.3.0)
rspec-mocks (3.3.2)
diff-lcs (>= 1.2.0, < 2.0)
rspec-support (~> 3.2.0)
rspec-rails (3.2.0)
actionpack (>= 3.0, <= 4.2)
activesupport (>= 3.0, <= 4.2)
railties (>= 3.0, <= 4.2)
rspec-core (~> 3.2.0)
rspec-expectations (~> 3.2.0)
rspec-mocks (~> 3.2.0)
rspec-support (~> 3.2.0)
rspec-support (3.2.1)
ruby-progressbar (1.7.1)
sass (3.4.11)
sass-rails (5.0.1)
rspec-support (~> 3.3.0)
rspec-rails (3.3.3)
actionpack (>= 3.0, < 4.3)
activesupport (>= 3.0, < 4.3)
railties (>= 3.0, < 4.3)
rspec-core (~> 3.3.0)
rspec-expectations (~> 3.3.0)
rspec-mocks (~> 3.3.0)
rspec-support (~> 3.3.0)
rspec-support (3.3.0)
ruby-progressbar (1.7.5)
sass (3.4.16)
sass-rails (5.0.3)
railties (>= 4.0.0, < 5.0)
sass (~> 3.1)
sprockets (>= 2.8, < 4.0)
@ -202,29 +197,24 @@ GEM
shellany (0.0.1)
shoulda-context (1.2.1)
slop (3.6.0)
spring (1.2.0)
spring (1.3.6)
spring-commands-rspec (1.0.4)
spring (>= 0.9.1)
sprockets (2.12.3)
hike (~> 1.2)
multi_json (~> 1.0)
sprockets (3.2.0)
rack (~> 1.0)
tilt (~> 1.1, != 1.3.0)
sprockets-rails (2.2.4)
sprockets-rails (2.3.2)
actionpack (>= 3.0)
activesupport (>= 3.0)
sprockets (>= 2.8, < 4.0)
sqlite3 (1.3.10)
thor (0.19.1)
thread_safe (0.3.4)
thread_safe (0.3.5)
tilt (1.4.1)
timers (4.0.1)
hitimes
turbolinks (2.5.3)
coffee-rails
tzinfo (1.2.2)
thread_safe (~> 0.1)
uglifier (2.7.0)
uglifier (2.7.1)
execjs (>= 0.3.0)
json (>= 1.8.0)
yajl-ruby (1.2.1)

View File

@ -2,7 +2,6 @@ require 'shoulda/matchers/active_model/helpers'
require 'shoulda/matchers/active_model/validation_matcher'
require 'shoulda/matchers/active_model/validator'
require 'shoulda/matchers/active_model/strict_validator'
require 'shoulda/matchers/active_model/validator_with_captured_range_error'
require 'shoulda/matchers/active_model/allow_value_matcher'
require 'shoulda/matchers/active_model/disallow_value_matcher'
require 'shoulda/matchers/active_model/validate_length_of_matcher'

View File

@ -304,23 +304,9 @@ module Shoulda
end
def set_attribute(value)
set_attribute_ignoring_range_errors(value)
after_setting_value_callback.call
end
def set_attribute_ignoring_range_errors(value)
instance.__send__("#{attribute_to_set}=", value)
ensure_that_attribute_has_been_changed_to_or_from_nil!(value)
rescue RangeError => exception
# Have to reset the attribute so that we don't get a RangeError the
# next time we attempt to write the attribute (ActiveRecord seems to
# set the attribute to the "bad" value anyway)
reset_attribute
validator.capture_range_error(exception)
end
def reset_attribute
instance.send(:raw_write_attribute, attribute_to_set, nil)
after_setting_value_callback.call
end
def ensure_that_attribute_has_been_changed_to_or_from_nil!(expected_value)

View File

@ -23,11 +23,6 @@ module Shoulda
end
end
def capture_range_error(exception)
@captured_range_error = exception
extend ValidatorWithCapturedRangeError
end
def allow_description(allowed_values)
"allow #{attribute} to be set to #{allowed_values}"
end
@ -85,9 +80,6 @@ module Shoulda
def collect_errors_or_exceptions
collect_messages
rescue RangeError => exception
capture_range_error(exception)
[]
end
def validation_errors

View File

@ -1,12 +0,0 @@
module Shoulda
module Matchers
module ActiveModel
# @private
module ValidatorWithCapturedRangeError
def messages_description
' RangeError: ' + captured_range_error.message.inspect
end
end
end
end
end

View File

@ -9,10 +9,6 @@ module UnitTests
Tests::Version.new(ActiveRecord::VERSION::STRING)
end
def active_record_can_raise_range_error?
active_record_version >= 4.2
end
def active_record_supports_enum?
defined?(::ActiveRecord::Enum)
end

View File

@ -241,88 +241,6 @@ describe Shoulda::Matchers::ActiveModel::AllowValueMatcher, type: :model do
end
end
if active_record_can_raise_range_error?
context 'when the value is outside of the range of the column' do
context 'not qualified with strict' do
it 'rejects, failing with the correct message' do
type = :integer
attribute_options = { type: type, options: { limit: 2 } }
record = define_model(:example, attr: attribute_options).new
assertion = -> { expect(record).to allow_value(100000).for(:attr) }
column_type_class = column_type_class_for(type)
message = <<-MESSAGE.strip_heredoc.strip
Did not expect errors when attr is set to 100000,
got RangeError: "100000 is out of range for #{column_type_class} with limit 2"
MESSAGE
expect(&assertion).to fail_with_message(message)
end
context 'qualified with a message' do
it 'ignores any specified message, failing with the correct message' do
type = :integer
attribute_options = { type: type, options: { limit: 2 } }
record = define_model(:example, attr: attribute_options).new
assertion = -> do
expect(record).
to allow_value(100000).
for(:attr).
with_message('some message')
end
column_type_class = column_type_class_for(type)
message = <<-MESSAGE.strip_heredoc.strip
Did not expect errors to include "some message" when attr is set to 100000,
got RangeError: "100000 is out of range for #{column_type_class} with limit 2"
MESSAGE
expect(&assertion).to fail_with_message(message)
end
end
end
if active_model_supports_strict?
context 'qualified with strict' do
it 'rejects, failing with the correct message' do
type = :integer
attribute_options = { type: type, options: { limit: 2 } }
record = define_model(:example, attr: attribute_options).new
assertion = -> do
expect(record).
to allow_value(100000).
for(:attr).
strict
end
column_type_class = column_type_class_for(type)
message = <<-MESSAGE.strip_heredoc.strip
Did not expect an exception to have been raised when attr is set to 100000,
got RangeError: "100000 is out of range for #{column_type_class} with limit 2"
MESSAGE
expect(&assertion).to fail_with_message(message)
end
context 'qualified with a message' do
it 'ignores any specified message' do
type = :integer
attribute_options = { type: type, options: { limit: 2 } }
record = define_model(:example, attr: attribute_options).new
assertion = -> do
expect(record).
to allow_value(100000).
for(:attr).
with_message('some message').
strict
end
column_type_class = column_type_class_for(type)
message = <<-MESSAGE.strip_heredoc.strip
Did not expect exception to include "some message" when attr is set to 100000,
got RangeError: "100000 is out of range for #{column_type_class} with limit 2"
MESSAGE
expect(&assertion).to fail_with_message(message)
end
end
end
end
end
end
context 'when the attribute writer method ignores a non-nil value' do
context 'when the attribute has a reader method' do
it 'raises a CouldNotSetAttributeError' do

View File

@ -79,88 +79,6 @@ describe Shoulda::Matchers::ActiveModel::DisallowValueMatcher, type: :model do
end
end
if active_record_can_raise_range_error?
context 'when the value is outside of the range of the column' do
context 'not qualified with strict' do
it 'accepts, failing with the correct message' do
type = :integer
attribute_options = { type: type, options: { limit: 2 } }
record = define_model(:example, attr: attribute_options).new
assertion = -> { expect(record).not_to disallow_value(100000).for(:attr) }
column_type_class = column_type_class_for(type)
message = <<-MESSAGE.strip_heredoc.strip
Did not expect errors when attr is set to 100000,
got RangeError: "100000 is out of range for #{column_type_class} with limit 2"
MESSAGE
expect(&assertion).to fail_with_message(message)
end
context 'qualified with a message' do
it 'ignores any specified message, failing with the correct message' do
type = :integer
attribute_options = { type: type, options: { limit: 2 } }
record = define_model(:example, attr: attribute_options).new
assertion = -> do
expect(record).
not_to disallow_value(100000).
for(:attr).
with_message('some message')
end
column_type_class = column_type_class_for(type)
message = <<-MESSAGE.strip_heredoc.strip
Did not expect errors to include "some message" when attr is set to 100000,
got RangeError: "100000 is out of range for #{column_type_class} with limit 2"
MESSAGE
expect(&assertion).to fail_with_message(message)
end
end
end
if active_model_supports_strict?
context 'qualified with strict' do
it 'accepts, failing with the correct message' do
type = :integer
attribute_options = { type: type, options: { limit: 2 } }
record = define_model(:example, attr: attribute_options).new
assertion = -> do
expect(record).
not_to disallow_value(100000).
for(:attr).
strict
end
column_type_class = column_type_class_for(type)
message = <<-MESSAGE.strip_heredoc.strip
Did not expect an exception to have been raised when attr is set to 100000,
got RangeError: "100000 is out of range for #{column_type_class} with limit 2"
MESSAGE
expect(&assertion).to fail_with_message(message)
end
context 'qualified with a message' do
it 'ignores any specified message' do
type = :integer
attribute_options = { type: type, options: { limit: 2 } }
record = define_model(:example, attr: attribute_options).new
assertion = -> do
expect(record).
not_to disallow_value(100000).
for(:attr).
with_message('some message').
strict
end
column_type_class = column_type_class_for(type)
message = <<-MESSAGE.strip_heredoc.strip
Did not expect exception to include "some message" when attr is set to 100000,
got RangeError: "100000 is out of range for #{column_type_class} with limit 2"
MESSAGE
expect(&assertion).to fail_with_message(message)
end
end
end
end
end
end
def matcher(value)
described_class.new(value)
end