diff options
Diffstat (limited to 'activemodel/lib/active_model/validations/acceptance.rb')
-rw-r--r-- | activemodel/lib/active_model/validations/acceptance.rb | 55 |
1 files changed, 55 insertions, 0 deletions
diff --git a/activemodel/lib/active_model/validations/acceptance.rb b/activemodel/lib/active_model/validations/acceptance.rb new file mode 100644 index 0000000000..ac5e79859b --- /dev/null +++ b/activemodel/lib/active_model/validations/acceptance.rb @@ -0,0 +1,55 @@ +module ActiveModel + + module Validations + class AcceptanceValidator < EachValidator # :nodoc: + def initialize(options) + super({ allow_nil: true, accept: "1" }.merge!(options)) + setup!(options[:class]) + end + + def validate_each(record, attribute, value) + unless value == options[:accept] + record.errors.add(attribute, :accepted, options.except(:accept, :allow_nil)) + end + end + + private + def setup!(klass) + attr_readers = attributes.reject { |name| klass.attribute_method?(name) } + attr_writers = attributes.reject { |name| klass.attribute_method?("#{name}=") } + klass.send(:attr_reader, *attr_readers) + klass.send(:attr_writer, *attr_writers) + end + end + + module HelperMethods + # Encapsulates the pattern of wanting to validate the acceptance of a + # terms of service check box (or similar agreement). + # + # class Person < ActiveRecord::Base + # validates_acceptance_of :terms_of_service + # validates_acceptance_of :eula, message: 'must be abided' + # end + # + # If the database column does not exist, the +terms_of_service+ attribute + # is entirely virtual. This check is performed only if +terms_of_service+ + # is not +nil+ and by default on save. + # + # Configuration options: + # * <tt>:message</tt> - A custom error message (default is: "must be + # accepted"). + # * <tt>:accept</tt> - Specifies value that is considered accepted. + # The default value is a string "1", which makes it easy to relate to + # an HTML checkbox. This should be set to +true+ if you are validating + # a database column, since the attribute is typecast from "1" to +true+ + # before validation. + # + # There is also a list of default options supported by every validator: + # +:if+, +:unless+, +:on+, +:allow_nil+, +:allow_blank+, and +:strict+. + # See <tt>ActiveModel::Validation#validates</tt> for more information. + def validates_acceptance_of(*attr_names) + validates_with AcceptanceValidator, _merge_attributes(attr_names) + end + end + end +end |