Add the qualifier allow_blank to validate_length_of (#1318)
Co-authored-by: Elliot Winkler <elliot.winkler@gmail.com>
This commit is contained in:
parent
421a49d0b6
commit
a4289e9651
|
@ -311,15 +311,6 @@ EOT
|
|||
self
|
||||
end
|
||||
|
||||
def allow_blank
|
||||
@options[:allow_blank] = true
|
||||
self
|
||||
end
|
||||
|
||||
def expects_to_allow_blank?
|
||||
@options[:allow_blank]
|
||||
end
|
||||
|
||||
def allow_nil
|
||||
@options[:allow_nil] = true
|
||||
self
|
||||
|
@ -423,14 +414,14 @@ EOT
|
|||
allows_all_values_in_array? &&
|
||||
disallows_all_values_outside_of_array? &&
|
||||
allows_nil_value? &&
|
||||
allows_blank_value?
|
||||
allow_blank_matches?
|
||||
end
|
||||
|
||||
def does_not_match_for_array?
|
||||
disallows_any_values_in_array? ||
|
||||
allows_any_value_outside_of_array? ||
|
||||
disallows_nil_value? ||
|
||||
disallows_blank_value?
|
||||
allow_blank_does_not_match?
|
||||
end
|
||||
|
||||
def allows_lower_value
|
||||
|
@ -616,16 +607,6 @@ EOT
|
|||
@options[:allow_nil] && disallows_value_of(nil)
|
||||
end
|
||||
|
||||
def allows_blank_value?
|
||||
@options[:allow_blank] != true ||
|
||||
BLANK_VALUES.all? { |value| allows_value_of(value) }
|
||||
end
|
||||
|
||||
def disallows_blank_value?
|
||||
@options[:allow_blank] &&
|
||||
BLANK_VALUES.any? { |value| disallows_value_of(value) }
|
||||
end
|
||||
|
||||
def inspected_array
|
||||
Shoulda::Matchers::Util.inspect_values(@array).to_sentence(
|
||||
two_words_connector: " or ",
|
||||
|
|
|
@ -232,13 +232,34 @@ module Shoulda
|
|||
# it { should validate_length_of(:bio).is_at_least(15).allow_nil }
|
||||
# end
|
||||
#
|
||||
# # Test::Unit
|
||||
# # Minitest (Shoulda)
|
||||
# class UserTest < ActiveSupport::TestCase
|
||||
# should validate_length_of(:bio).is_at_least(15).allow_nil
|
||||
# end
|
||||
#
|
||||
# @return [ValidateLengthOfMatcher]
|
||||
#
|
||||
# # ##### allow_blank
|
||||
#
|
||||
# Use `allow_blank` to assert that the attribute allows blank.
|
||||
#
|
||||
# class User
|
||||
# include ActiveModel::Model
|
||||
# attr_accessor :bio
|
||||
#
|
||||
# validates_length_of :bio, minimum: 15, allow_blank: true
|
||||
# end
|
||||
#
|
||||
# # RSpec
|
||||
# describe User do
|
||||
# it { should validate_length_of(:bio).is_at_least(15).allow_blank }
|
||||
# end
|
||||
#
|
||||
# # Minitest (Shoulda)
|
||||
# class UserTest < ActiveSupport::TestCase
|
||||
# should validate_length_of(:bio).is_at_least(15).allow_blank
|
||||
# end
|
||||
#
|
||||
def validate_length_of(attr)
|
||||
ValidateLengthOfMatcher.new(attr)
|
||||
end
|
||||
|
@ -331,7 +352,8 @@ module Shoulda
|
|||
|
||||
lower_bound_matches? &&
|
||||
upper_bound_matches? &&
|
||||
allow_nil_matches?
|
||||
allow_nil_matches? &&
|
||||
allow_blank_matches?
|
||||
end
|
||||
|
||||
def does_not_match?(subject)
|
||||
|
@ -339,7 +361,8 @@ module Shoulda
|
|||
|
||||
lower_bound_does_not_match? ||
|
||||
upper_bound_does_not_match? ||
|
||||
allow_nil_does_not_match?
|
||||
allow_nil_does_not_match? ||
|
||||
allow_blank_does_not_match?
|
||||
end
|
||||
|
||||
private
|
||||
|
@ -376,6 +399,7 @@ module Shoulda
|
|||
def disallows_lower_length?
|
||||
!@options.key?(:minimum) ||
|
||||
@options[:minimum] == 0 ||
|
||||
(@options[:minimum] == 1 && expects_to_allow_blank?) ||
|
||||
disallows_length_of?(
|
||||
@options[:minimum] - 1,
|
||||
translated_short_message
|
||||
|
|
|
@ -24,6 +24,11 @@ module Shoulda
|
|||
self
|
||||
end
|
||||
|
||||
def allow_blank
|
||||
options[:allow_blank] = true
|
||||
self
|
||||
end
|
||||
|
||||
def strict
|
||||
@expects_strict = true
|
||||
self
|
||||
|
@ -116,8 +121,20 @@ module Shoulda
|
|||
)
|
||||
end
|
||||
|
||||
def allow_blank_matches?
|
||||
!expects_to_allow_blank? ||
|
||||
blank_values.all? { |value| allows_value_of(value) }
|
||||
end
|
||||
|
||||
def allow_blank_does_not_match?
|
||||
expects_to_allow_blank? &&
|
||||
blank_values.all? { |value| disallows_value_of(value) }
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
attr_reader :options
|
||||
|
||||
def overall_failure_message
|
||||
Shoulda::Matchers.word_wrap(
|
||||
"Expected #{model.name} to #{description}, but this could not be " +
|
||||
|
@ -161,6 +178,14 @@ module Shoulda
|
|||
@last_submatcher_run = matcher
|
||||
matcher.matches?(subject)
|
||||
end
|
||||
|
||||
def expects_to_allow_blank?
|
||||
options[:allow_blank]
|
||||
end
|
||||
|
||||
def blank_values
|
||||
['', ' ', "\n", "\r", "\t", "\f"]
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
@ -311,6 +311,62 @@ this could not be proved.
|
|||
end
|
||||
end
|
||||
|
||||
context 'qualified with allow_blank' do
|
||||
context 'and validating with allow_blank' do
|
||||
context 'with minimum' do
|
||||
context 'and minimum is 1' do
|
||||
it 'accepts' do
|
||||
expect(validating_length(minimum: 1, allow_blank: true)).
|
||||
to validate_length_of(:attr).is_at_least(1).allow_blank
|
||||
end
|
||||
end
|
||||
|
||||
context 'and minimum is greater than 1' do
|
||||
it 'accepts' do
|
||||
expect(validating_length(minimum: 2, allow_blank: true)).
|
||||
to validate_length_of(:attr).is_at_least(2).allow_blank
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
context 'with maximum' do
|
||||
context 'and maximum is 0' do
|
||||
it 'accepts' do
|
||||
expect(validating_length(maximum: 0, allow_blank: true)).
|
||||
to validate_length_of(:attr).is_at_most(0).allow_blank
|
||||
end
|
||||
end
|
||||
|
||||
context 'and maximum is greater than 0' do
|
||||
it 'accepts' do
|
||||
expect(validating_length(maximum: 1, allow_blank: true)).
|
||||
to validate_length_of(:attr).is_at_most(1).allow_blank
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
context 'and not validating with allow_blank' do
|
||||
it 'rejects' do
|
||||
assertion = lambda do
|
||||
expect(validating_length(minimum: 1)).
|
||||
to validate_length_of(:attr).is_at_least(1).allow_blank
|
||||
end
|
||||
|
||||
message = <<-MESSAGE
|
||||
Expected Example to validate that the length of :attr is at least 1, but
|
||||
this could not be proved.
|
||||
After setting :attr to ‹""›, the matcher expected the Example to be
|
||||
valid, but it was invalid instead, producing these validation errors:
|
||||
|
||||
* attr: ["is too short (minimum is 1 character)"]
|
||||
MESSAGE
|
||||
|
||||
expect(&assertion).to fail_with_message(message)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def define_model_validating_length(options = {})
|
||||
options = options.dup
|
||||
attribute_name = options.delete(:attribute_name) { :attr }
|
||||
|
|
Loading…
Reference in New Issue