Implemented strict validation concept
In order to deliver debug information to dev team instead of display error message to end user Implemented strict validation concept that suppose to define validation that always raise exception when fails
This commit is contained in:
parent
5912f3f97e
commit
8620bf90c5
@ -63,7 +63,7 @@ module ActiveModel
|
|||||||
class Errors
|
class Errors
|
||||||
include Enumerable
|
include Enumerable
|
||||||
|
|
||||||
CALLBACKS_OPTIONS = [:if, :unless, :on, :allow_nil, :allow_blank]
|
CALLBACKS_OPTIONS = [:if, :unless, :on, :allow_nil, :allow_blank, :strict]
|
||||||
|
|
||||||
attr_reader :messages
|
attr_reader :messages
|
||||||
|
|
||||||
@ -218,6 +218,9 @@ def add(attribute, message = nil, options = {})
|
|||||||
elsif message.is_a?(Proc)
|
elsif message.is_a?(Proc)
|
||||||
message = message.call
|
message = message.call
|
||||||
end
|
end
|
||||||
|
if options[:strict]
|
||||||
|
raise ActiveModel::StrictValidationFailed, message
|
||||||
|
end
|
||||||
|
|
||||||
self[attribute] << message
|
self[attribute] << message
|
||||||
end
|
end
|
||||||
@ -319,4 +322,7 @@ def generate_message(attribute, type = :invalid, options = {})
|
|||||||
I18n.translate(key, options)
|
I18n.translate(key, options)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
class StrictValidationFailed < StandardError
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
@ -58,6 +58,8 @@ module HelperMethods
|
|||||||
# <tt>:unless => Proc.new { |user| user.signup_step <= 2 }</tt>).
|
# <tt>:unless => Proc.new { |user| user.signup_step <= 2 }</tt>).
|
||||||
# The method, proc or string should return or evaluate to a true or
|
# The method, proc or string should return or evaluate to a true or
|
||||||
# false value.
|
# false value.
|
||||||
|
# * <tt>:strict</tt> - Specifies whether validation should be strict.
|
||||||
|
# See <tt>ActiveModel::Validation#validates!</tt> for more information
|
||||||
def validates_acceptance_of(*attr_names)
|
def validates_acceptance_of(*attr_names)
|
||||||
validates_with AcceptanceValidator, _merge_attributes(attr_names)
|
validates_with AcceptanceValidator, _merge_attributes(attr_names)
|
||||||
end
|
end
|
||||||
|
@ -58,6 +58,8 @@ module HelperMethods
|
|||||||
# <tt>:unless => :skip_validation</tt>, or
|
# <tt>:unless => :skip_validation</tt>, or
|
||||||
# <tt>:unless => Proc.new { |user| user.signup_step <= 2 }</tt>). The
|
# <tt>:unless => Proc.new { |user| user.signup_step <= 2 }</tt>). The
|
||||||
# method, proc or string should return or evaluate to a true or false value.
|
# method, proc or string should return or evaluate to a true or false value.
|
||||||
|
# * <tt>:strict</tt> - Specifies whether validation should be strict.
|
||||||
|
# See <tt>ActiveModel::Validation#validates!</tt> for more information
|
||||||
def validates_confirmation_of(*attr_names)
|
def validates_confirmation_of(*attr_names)
|
||||||
validates_with ConfirmationValidator, _merge_attributes(attr_names)
|
validates_with ConfirmationValidator, _merge_attributes(attr_names)
|
||||||
end
|
end
|
||||||
|
@ -59,6 +59,8 @@ module HelperMethods
|
|||||||
# * <tt>:unless</tt> - Specifies a method, proc or string to call to determine if the validation should
|
# * <tt>:unless</tt> - Specifies a method, proc or string to call to determine if the validation should
|
||||||
# not occur (e.g. <tt>:unless => :skip_validation</tt>, or <tt>:unless => Proc.new { |user| user.signup_step <= 2 }</tt>). The
|
# not occur (e.g. <tt>:unless => :skip_validation</tt>, or <tt>:unless => Proc.new { |user| user.signup_step <= 2 }</tt>). The
|
||||||
# method, proc or string should return or evaluate to a true or false value.
|
# method, proc or string should return or evaluate to a true or false value.
|
||||||
|
# * <tt>:strict</tt> - Specifies whether validation should be strict.
|
||||||
|
# See <tt>ActiveModel::Validation#validates!</tt> for more information
|
||||||
def validates_exclusion_of(*attr_names)
|
def validates_exclusion_of(*attr_names)
|
||||||
validates_with ExclusionValidator, _merge_attributes(attr_names)
|
validates_with ExclusionValidator, _merge_attributes(attr_names)
|
||||||
end
|
end
|
||||||
|
@ -84,6 +84,8 @@ module HelperMethods
|
|||||||
# * <tt>:unless</tt> - Specifies a method, proc or string to call to determine if the validation should
|
# * <tt>:unless</tt> - Specifies a method, proc or string to call to determine if the validation should
|
||||||
# not occur (e.g. <tt>:unless => :skip_validation</tt>, or <tt>:unless => Proc.new { |user| user.signup_step <= 2 }</tt>). The
|
# not occur (e.g. <tt>:unless => :skip_validation</tt>, or <tt>:unless => Proc.new { |user| user.signup_step <= 2 }</tt>). The
|
||||||
# method, proc or string should return or evaluate to a true or false value.
|
# method, proc or string should return or evaluate to a true or false value.
|
||||||
|
# * <tt>:strict</tt> - Specifies whether validation should be strict.
|
||||||
|
# See <tt>ActiveModel::Validation#validates!</tt> for more information
|
||||||
def validates_format_of(*attr_names)
|
def validates_format_of(*attr_names)
|
||||||
validates_with FormatValidator, _merge_attributes(attr_names)
|
validates_with FormatValidator, _merge_attributes(attr_names)
|
||||||
end
|
end
|
||||||
|
@ -59,6 +59,8 @@ module HelperMethods
|
|||||||
# * <tt>:unless</tt> - Specifies a method, proc or string to call to determine if the validation should
|
# * <tt>:unless</tt> - Specifies a method, proc or string to call to determine if the validation should
|
||||||
# not occur (e.g. <tt>:unless => :skip_validation</tt>, or <tt>:unless => Proc.new { |user| user.signup_step <= 2 }</tt>). The
|
# not occur (e.g. <tt>:unless => :skip_validation</tt>, or <tt>:unless => Proc.new { |user| user.signup_step <= 2 }</tt>). The
|
||||||
# method, proc or string should return or evaluate to a true or false value.
|
# method, proc or string should return or evaluate to a true or false value.
|
||||||
|
# * <tt>:strict</tt> - Specifies whether validation should be strict.
|
||||||
|
# See <tt>ActiveModel::Validation#validates!</tt> for more information
|
||||||
def validates_inclusion_of(*attr_names)
|
def validates_inclusion_of(*attr_names)
|
||||||
validates_with InclusionValidator, _merge_attributes(attr_names)
|
validates_with InclusionValidator, _merge_attributes(attr_names)
|
||||||
end
|
end
|
||||||
|
@ -96,6 +96,8 @@ module HelperMethods
|
|||||||
# * <tt>:tokenizer</tt> - Specifies how to split up the attribute string. (e.g. <tt>:tokenizer => lambda {|str| str.scan(/\w+/)}</tt> to
|
# * <tt>:tokenizer</tt> - Specifies how to split up the attribute string. (e.g. <tt>:tokenizer => lambda {|str| str.scan(/\w+/)}</tt> to
|
||||||
# count words as in above example.)
|
# count words as in above example.)
|
||||||
# Defaults to <tt>lambda{ |value| value.split(//) }</tt> which counts individual characters.
|
# Defaults to <tt>lambda{ |value| value.split(//) }</tt> which counts individual characters.
|
||||||
|
# * <tt>:strict</tt> - Specifies whether validation should be strict.
|
||||||
|
# See <tt>ActiveModel::Validation#validates!</tt> for more information
|
||||||
def validates_length_of(*attr_names)
|
def validates_length_of(*attr_names)
|
||||||
validates_with LengthValidator, _merge_attributes(attr_names)
|
validates_with LengthValidator, _merge_attributes(attr_names)
|
||||||
end
|
end
|
||||||
|
@ -107,6 +107,8 @@ module HelperMethods
|
|||||||
# * <tt>:unless</tt> - Specifies a method, proc or string to call to determine if the validation should
|
# * <tt>:unless</tt> - Specifies a method, proc or string to call to determine if the validation should
|
||||||
# not occur (e.g. <tt>:unless => :skip_validation</tt>, or <tt>:unless => Proc.new { |user| user.signup_step <= 2 }</tt>). The
|
# not occur (e.g. <tt>:unless => :skip_validation</tt>, or <tt>:unless => Proc.new { |user| user.signup_step <= 2 }</tt>). The
|
||||||
# method, proc or string should return or evaluate to a true or false value.
|
# method, proc or string should return or evaluate to a true or false value.
|
||||||
|
# * <tt>:strict</tt> - Specifies whether validation should be strict.
|
||||||
|
# See <tt>ActiveModel::Validation#validates!</tt> for more information
|
||||||
#
|
#
|
||||||
# The following checks can also be supplied with a proc or a symbol which corresponds to a method:
|
# The following checks can also be supplied with a proc or a symbol which corresponds to a method:
|
||||||
# * <tt>:greater_than</tt>
|
# * <tt>:greater_than</tt>
|
||||||
|
@ -35,6 +35,8 @@ module HelperMethods
|
|||||||
# * <tt>unless</tt> - Specifies a method, proc or string to call to determine if the validation should
|
# * <tt>unless</tt> - Specifies a method, proc or string to call to determine if the validation should
|
||||||
# not occur (e.g. <tt>:unless => :skip_validation</tt>, or <tt>:unless => Proc.new { |user| user.signup_step <= 2 }</tt>).
|
# not occur (e.g. <tt>:unless => :skip_validation</tt>, or <tt>:unless => Proc.new { |user| user.signup_step <= 2 }</tt>).
|
||||||
# The method, proc or string should return or evaluate to a true or false value.
|
# The method, proc or string should return or evaluate to a true or false value.
|
||||||
|
# * <tt>:strict</tt> - Specifies whether validation should be strict.
|
||||||
|
# See <tt>ActiveModel::Validation#validates!</tt> for more information
|
||||||
#
|
#
|
||||||
def validates_presence_of(*attr_names)
|
def validates_presence_of(*attr_names)
|
||||||
validates_with PresenceValidator, _merge_attributes(attr_names)
|
validates_with PresenceValidator, _merge_attributes(attr_names)
|
||||||
|
@ -70,8 +70,8 @@ module ClassMethods
|
|||||||
# validator's initializer as +options[:in]+ while other types including
|
# validator's initializer as +options[:in]+ while other types including
|
||||||
# regular expressions and strings are passed as +options[:with]+
|
# regular expressions and strings are passed as +options[:with]+
|
||||||
#
|
#
|
||||||
# Finally, the options +:if+, +:unless+, +:on+, +:allow_blank+ and +:allow_nil+ can be given
|
# Finally, the options +:if+, +:unless+, +:on+, +:allow_blank+, +:allow_nil+ and +:strict+
|
||||||
# to one specific validator, as a hash:
|
# can be given to one specific validator, as a hash:
|
||||||
#
|
#
|
||||||
# validates :password, :presence => { :if => :password_required? }, :confirmation => true
|
# validates :password, :presence => { :if => :password_required? }, :confirmation => true
|
||||||
#
|
#
|
||||||
@ -101,12 +101,24 @@ def validates(*attributes)
|
|||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
# This method is used to define validation that can not be correcterized by end user
|
||||||
|
# and is considered exceptional.
|
||||||
|
# So each validator defined with bang or <tt>:strict</tt> option set to <tt>true</tt>
|
||||||
|
# will always raise <tt>ActiveModel::InternalValidationFailed</tt> instead of adding error
|
||||||
|
# when validation fails
|
||||||
|
# See <tt>validates</tt> for more information about validation itself.
|
||||||
|
def validates!(*attributes)
|
||||||
|
options = attributes.extract_options!
|
||||||
|
options[:strict] = true
|
||||||
|
validates(*(attributes << options))
|
||||||
|
end
|
||||||
|
|
||||||
protected
|
protected
|
||||||
|
|
||||||
# When creating custom validators, it might be useful to be able to specify
|
# When creating custom validators, it might be useful to be able to specify
|
||||||
# additional default keys. This can be done by overwriting this method.
|
# additional default keys. This can be done by overwriting this method.
|
||||||
def _validates_default_keys
|
def _validates_default_keys
|
||||||
[ :if, :unless, :on, :allow_blank, :allow_nil ]
|
[ :if, :unless, :on, :allow_blank, :allow_nil , :strict]
|
||||||
end
|
end
|
||||||
|
|
||||||
def _parse_validates_options(options) #:nodoc:
|
def _parse_validates_options(options) #:nodoc:
|
||||||
|
@ -61,7 +61,9 @@ module ClassMethods
|
|||||||
# (e.g. <tt>:unless => :skip_validation</tt>, or
|
# (e.g. <tt>:unless => :skip_validation</tt>, or
|
||||||
# <tt>:unless => Proc.new { |user| user.signup_step <= 2 }</tt>).
|
# <tt>:unless => Proc.new { |user| user.signup_step <= 2 }</tt>).
|
||||||
# The method, proc or string should return or evaluate to a true or false value.
|
# The method, proc or string should return or evaluate to a true or false value.
|
||||||
#
|
# * <tt>:strict</tt> - Specifies whether validation should be strict.
|
||||||
|
# See <tt>ActiveModel::Validation#validates!</tt> for more information
|
||||||
|
|
||||||
# If you pass any additional configuration options, they will be passed
|
# If you pass any additional configuration options, they will be passed
|
||||||
# to the class and available as <tt>options</tt>:
|
# to the class and available as <tt>options</tt>:
|
||||||
#
|
#
|
||||||
@ -140,4 +142,4 @@ def validates_with(*args, &block)
|
|||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
@ -297,4 +297,37 @@ def test_validations_on_the_instance_level
|
|||||||
|
|
||||||
assert auto.valid?
|
assert auto.valid?
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def test_strict_validation_in_validates
|
||||||
|
Topic.validates :title, :strict => true, :presence => true
|
||||||
|
assert_raises ActiveModel::StrictValidationFailed do
|
||||||
|
Topic.new.valid?
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
def test_strict_validation_not_fails
|
||||||
|
Topic.validates :title, :strict => true, :presence => true
|
||||||
|
assert Topic.new(:title => "hello").valid?
|
||||||
|
end
|
||||||
|
|
||||||
|
def test_strict_validation_particular_validator
|
||||||
|
Topic.validates :title, :presence => {:strict => true}
|
||||||
|
assert_raises ActiveModel::StrictValidationFailed do
|
||||||
|
Topic.new.valid?
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
def test_strict_validation_in_custom_validator_helper
|
||||||
|
Topic.validates_presence_of :title, :strict => true
|
||||||
|
assert_raises ActiveModel::StrictValidationFailed do
|
||||||
|
Topic.new.valid?
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
def test_validates_with_bang
|
||||||
|
Topic.validates! :title, :presence => true
|
||||||
|
assert_raises ActiveModel::StrictValidationFailed do
|
||||||
|
Topic.new.valid?
|
||||||
|
end
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
Loading…
Reference in New Issue
Block a user