Module: Remarkable::ActiveRecord::Matchers

Included in:
Macros, Spec::Rails::Example::ModelExampleGroup
Defined in:
lib/remarkable/active_record/macros/database/index_matcher.rb,
lib/remarkable/active_record/macros/callbacks/callback_matcher.rb,
lib/remarkable/active_record/macros/database/have_db_column_matcher.rb,
lib/remarkable/active_record/macros/associations/association_matcher.rb,
lib/remarkable/active_record/macros/validations/have_named_scope_matcher.rb,
lib/remarkable/active_record/macros/validations/have_class_methods_matcher.rb,
lib/remarkable/active_record/macros/validations/protect_attributes_matcher.rb,
lib/remarkable/active_record/macros/validations/validate_format_of_matcher.rb,
lib/remarkable/active_record/macros/validations/validate_length_of_matcher.rb,
lib/remarkable/active_record/macros/validations/validate_associated_matcher.rb,
lib/remarkable/active_record/macros/validations/ensure_value_in_list_matcher.rb,
lib/remarkable/active_record/macros/validations/validate_presence_of_matcher.rb,
lib/remarkable/active_record/macros/validations/ensure_value_in_range_matcher.rb,
lib/remarkable/active_record/macros/validations/have_instance_methods_matcher.rb,
lib/remarkable/active_record/macros/validations/validate_exclusion_of_matcher.rb,
lib/remarkable/active_record/macros/validations/validate_inclusion_of_matcher.rb,
lib/remarkable/active_record/macros/validations/validate_acceptance_of_matcher.rb,
lib/remarkable/active_record/macros/validations/validate_uniqueness_of_matcher.rb,
lib/remarkable/active_record/macros/validations/allow_mass_assignment_of_matcher.rb,
lib/remarkable/active_record/macros/validations/have_readonly_attributes_matcher.rb,
lib/remarkable/active_record/macros/validations/validate_confirmation_of_matcher.rb,
lib/remarkable/active_record/macros/validations/validate_numericality_of_matcher.rb

Overview

:nodoc:

Defined Under Namespace

Classes: AllowMassAssignmentOfMatcher, AssociationMatcher, CallbackMatcher, ColumnMatcher, EnsureValueInListMatcher, EnsureValueInRangeMatcher, HaveClassMethods, HaveInstanceMethods, HaveNamedScope, HaveReadonlyAttributes, IndexMatcher, ProtectAttributes, ValidateAcceptanceOfMatcher, ValidateAssociatedMatcher, ValidateConfirmationOfMatcher, ValidateLengthOfMatcher, ValidateNumericalityOfMatcher, ValidatePresenceOfMatcher, ValidateUniquenessOfMatcher

Instance Method Summary collapse

Instance Method Details

#allow_mass_assignment_of(*attributes) ⇒ Object

Ensures that the attribute can be set on mass update.

it { should allow_mass_assignment_of(:email, :name) }


47
48
49
# File 'lib/remarkable/active_record/macros/validations/allow_mass_assignment_of_matcher.rb', line 47

def allow_mass_assignment_of(*attributes)
  AllowMassAssignmentOfMatcher.new(*attributes)
end

#belong_to(*associations) ⇒ Object

Ensure that the belongs_to relationship exists.

Examples:

should_belong_to :parent
it { should belong_to(:parent) }


188
189
190
# File 'lib/remarkable/active_record/macros/associations/association_matcher.rb', line 188

def belong_to(*associations)
  AssociationMatcher.new(:belongs_to, *associations)
end

#ensure_inclusion_of(attribute, *good_values) ⇒ Object

TODO This one is for shoulda compatibility. Deprecate it?



53
54
55
56
57
# File 'lib/remarkable/active_record/macros/validations/validate_inclusion_of_matcher.rb', line 53

def ensure_inclusion_of(attribute, *good_values) #:nodoc:
  warn "[DEPRECATION] should_ensure_inclusion_of is deprecated. " <<
       "Use should_validate_inclusion_of instead."
  validate_inclusion_of(attribute, *good_values)
end

#ensure_length_at_least(attribute, range, options = {}) ⇒ Object

TODO Deprecate me



203
204
205
206
207
# File 'lib/remarkable/active_record/macros/validations/validate_length_of_matcher.rb', line 203

def ensure_length_at_least(attribute, range, options = {}) #:nodoc:
  warn "[DEPRECATION] should_ensure_length_at_least is deprecated. " <<
       "Use should_validate_length_of(#{attribute.inspect}, :minimum => #{range.inspect}) instead."
  ValidateLengthOfMatcher.new(:minimum, range, attribute, options)
end

#ensure_length_in_range(attribute, range, options = {}) ⇒ Object

TODO Deprecate me



196
197
198
199
200
# File 'lib/remarkable/active_record/macros/validations/validate_length_of_matcher.rb', line 196

def ensure_length_in_range(attribute, range, options = {}) #:nodoc:
  warn "[DEPRECATION] should_ensure_length_in_range is deprecated. " <<
       "Use should_validate_length_of(#{attribute.inspect}, :in => #{range.inspect}) instead."
  ValidateLengthOfMatcher.new(:within, range, attribute, options)
end

#ensure_length_is(attribute, range, options = {}) ⇒ Object

TODO Deprecate me



210
211
212
213
214
# File 'lib/remarkable/active_record/macros/validations/validate_length_of_matcher.rb', line 210

def ensure_length_is(attribute, range, options = {}) #:nodoc:
  warn "[DEPRECATION] should_ensure_length_is is deprecated. " <<
       "Use should_validate_length_of(#{attribute.inspect}, :is => #{range.inspect}) instead."
  ValidateLengthOfMatcher.new(:is, range, attribute, options)
end

#ensure_length_of(*attributes) ⇒ Object

TODO This one is for shoulda compatibility. Deprecate it?



189
190
191
192
193
# File 'lib/remarkable/active_record/macros/validations/validate_length_of_matcher.rb', line 189

def ensure_length_of(*attributes) #:nodoc:
  warn "[DEPRECATION] should_ensure_length_of is deprecated. " <<
       "Use should_validate_length_of instead."
  validate_length_of(*attributes)
end

#ensure_value_in_range(attribute, range, *options) ⇒ Object

TODO Deprecate this method, but not the matcher.



144
145
146
147
148
149
150
151
152
153
154
155
156
157
# File 'lib/remarkable/active_record/macros/validations/ensure_value_in_range_matcher.rb', line 144

def ensure_value_in_range(attribute, range, *options) #:nodoc:
  hash_options = options.extract_options!

  warn "[DEPRECATION] should_ensure_value_in_range with :low_message is deprecated. " <<
       "Use should_validate_inclusion_of with :message instead." if hash_options[:low_message]

  warn "[DEPRECATION] should_ensure_value_in_range with :high_message is deprecated. " <<
       "Use should_validate_inclusion_of with :message instead." if hash_options[:high_message]

  warn "[DEPRECATION] should_ensure_value_in_range is deprecated. " <<
       "Use should_validate_inclusion_of instead." if hash_options[:low_message].blank? && hash_options[:high_message].blank?

  EnsureValueInRangeMatcher.new(attribute, :inclusion, range, *options)
end

#have_and_belong_to_many(*associations) ⇒ Object

Ensures that the has_and_belongs_to_many relationship exists, and that the join table is in place.

Examples:

should_have_and_belong_to_many :posts, :cars
it{ should have_and_belong_to_many :posts, :cars }


236
237
238
# File 'lib/remarkable/active_record/macros/associations/association_matcher.rb', line 236

def have_and_belong_to_many(*associations)
  AssociationMatcher.new(:has_and_belongs_to_many, *associations)
end

#have_class_methods(*methods) ⇒ Object

Ensure that the given class methods are defined on the model.

it { should have_class_methods(:find, :destroy) }


49
50
51
# File 'lib/remarkable/active_record/macros/validations/have_class_methods_matcher.rb', line 49

def have_class_methods(*methods)
  HaveClassMethods.new(*methods)
end

#have_db_column(column, options = {}) ⇒ Object

Ensures that a column of the database actually exists.

Options:

  • type - database column types like :string, :integer, etc.

  • All options available in migrations are also available here. (.type, .default, .precision, .limit, .scale, .sql_type, .primary, .null)

  • with_options - option used to load the above options via hash (:type => :string, :primary => true, etc.)

Example: it { should have_db_column(:name).type(:string) } it { should have_db_column(:age).with_options(:type => :integer) } it { should_not have_db_column(:salary) }



96
97
98
# File 'lib/remarkable/active_record/macros/database/have_db_column_matcher.rb', line 96

def have_db_column(column, options = {})
  ColumnMatcher.new(column, options)
end

#have_db_columns(*columns) ⇒ Object

Alias for #have_db_column



102
103
104
# File 'lib/remarkable/active_record/macros/database/have_db_column_matcher.rb', line 102

def have_db_columns(*columns)
  ColumnMatcher.new(*columns)
end

#have_indices(*columns) ⇒ Object Also known as: have_index

Ensures the database column has specified index.

Options:

  • unique - when supplied, tests if the index is unique or not

Example:

it { should have_index(:ssn).unique(true) }


81
82
83
# File 'lib/remarkable/active_record/macros/database/index_matcher.rb', line 81

def have_indices(*columns)
  IndexMatcher.new(*columns)
end

#have_instance_methods(*methods) ⇒ Object

Ensure that the given instance methods are defined on the model.

it { should have_instance_methods(:email, :name, :name=) }


49
50
51
# File 'lib/remarkable/active_record/macros/validations/have_instance_methods_matcher.rb', line 49

def have_instance_methods(*methods)
  HaveInstanceMethods.new(*methods)
end

#have_many(*associations) ⇒ Object

Ensures that the has_many relationship exists. Will also test that the associated table has the required columns. Works with polymorphic associations.

Options:

  • :through - association name for has_many :through

  • :dependent - tests that the association makes use of the dependent option.

Examples:

should_have_many :friends
should_have_many :enemies, :through => :friends
should_have_many :enemies, :dependent => :destroy

it{ should have_many(:friends) }
it{ should have_many(:enemies, :through => :friends) }
it{ should have_many(:enemies, :dependent => :destroy) }


210
211
212
# File 'lib/remarkable/active_record/macros/associations/association_matcher.rb', line 210

def have_many(*associations)
  AssociationMatcher.new(:has_many, *associations)
end

#have_named_scope(scope_call, *args) ⇒ Object

Ensures that the model has a method named scope_name that returns a NamedScope object with the proxy options set to the options you supply. scope_name can be either a symbol, or a method call which will be evaled against the model. The eval’d method call has access to all the same instance variables that a should statement would.

Options: Any of the options that the named scope would pass on to find.

Example:

it { should have_named_scope(:visible, :conditions => {:visible => true}) }

Passes for

named_scope :visible, :conditions => {:visible => true}

Or for

def self.visible
  scoped(:conditions => {:visible => true})
end

You can test lambdas or methods that return ActiveRecord#scoped calls:

it { should have_named_scope('recent(5)', :limit => 5) }
it { should have_named_scope('recent(1)', :limit => 1) }

Passes for

named_scope :recent, lambda {|c| {:limit => c}}

Or for

def self.recent(c)
  scoped(:limit => c)
end


89
90
91
# File 'lib/remarkable/active_record/macros/validations/have_named_scope_matcher.rb', line 89

def have_named_scope(scope_call, *args)
  HaveNamedScope.new(scope_call, *args)
end

#have_one(*associations) ⇒ Object

Ensure that the has_one relationship exists. Will also test that the associated table has the required columns. Works with polymorphic associations.

Options:

  • :dependent - tests that the association makes use of the dependent option.

Examples:

should_have_one :god
it{ should have_one(:god) }


225
226
227
# File 'lib/remarkable/active_record/macros/associations/association_matcher.rb', line 225

def have_one(*associations)
  AssociationMatcher.new(:has_one, *associations)
end

#have_readonly_attributes(*attributes) ⇒ Object

Ensures that the attribute cannot be changed once the record has been created.

it { should have_readonly_attributes(:password, :admin_flag) }


43
44
45
# File 'lib/remarkable/active_record/macros/validations/have_readonly_attributes_matcher.rb', line 43

def have_readonly_attributes(*attributes)
  HaveReadonlyAttributes.new(*attributes)
end

#only_allow_numeric_or_blank_values_for(*attributes) ⇒ Object

TODO Deprecate me



227
228
229
230
231
# File 'lib/remarkable/active_record/macros/validations/validate_numericality_of_matcher.rb', line 227

def only_allow_numeric_or_blank_values_for(*attributes)
  warn "[DEPRECATION] should_only_allow_numeric_or_blank_values_for is deprecated. " <<
       "Use should_validate_numericality_of with :allow_blank => true instead."
  ValidateNumericalityOfMatcher.new(*attributes).allow_blank
end

#only_allow_numeric_values_for(*attributes) ⇒ Object

TODO Deprecate me



220
221
222
223
224
# File 'lib/remarkable/active_record/macros/validations/validate_numericality_of_matcher.rb', line 220

def only_allow_numeric_values_for(*attributes) #:nodoc:
  warn "[DEPRECATION] should_only_allow_numeric_values_for is deprecated. " <<
       "Use should_validate_numericality_of instead."
  ValidateNumericalityOfMatcher.new(*attributes)
end

#protect_attributes(*attributes) ⇒ Object

TODO Deprecate this method and the matcher.



44
45
46
47
48
# File 'lib/remarkable/active_record/macros/validations/protect_attributes_matcher.rb', line 44

def protect_attributes(*attributes) #:nodoc:
  warn "[DEPRECATION] should_protect_attributes is deprecated. " <<
       "Use should_not_allow_mass_assignment_of instead."
  ProtectAttributes.new(*attributes)
end

#require_acceptance_of(*attributes) ⇒ Object

TODO Deprecate this method.



69
70
71
72
73
# File 'lib/remarkable/active_record/macros/validations/validate_acceptance_of_matcher.rb', line 69

def require_acceptance_of(*attributes) #:nodoc:
  warn "[DEPRECATION] should_require_acceptance_of is deprecated. " <<
       "Use should_validate_acceptance_of instead."
  ValidateAcceptanceOfMatcher.new(*attributes)
end

#require_attributes(*attributes) ⇒ Object

TODO Deprecate me



46
47
48
49
50
# File 'lib/remarkable/active_record/macros/validations/validate_presence_of_matcher.rb', line 46

def require_attributes(*attributes) #:nodoc:
  warn "[DEPRECATION] should_require_attributes is deprecated. " <<
       "Use should_validate_presence_of instead."
  ValidatePresenceOfMatcher.new(*attributes)
end

#require_unique_attributes(*attributes) ⇒ Object

TODO Deprecate this alias, the deprecation warning is the matcher



211
212
213
214
215
# File 'lib/remarkable/active_record/macros/validations/validate_uniqueness_of_matcher.rb', line 211

def require_unique_attributes(*attributes)
  warn "[DEPRECATION] should_require_unique_attributes is deprecated. " <<
       "Use should_validate_uniqueness_of instead."
  validate_uniqueness_of(*attributes)
end

#validate_acceptance_of(*attributes) ⇒ Object

Ensures that the model cannot be saved if one of the attributes listed is not accepted.

If an instance variable has been created in the setup named after the model being tested, then this method will use that. Otherwise, it will create a new instance to test against.

Options:

  • :accept - the expected value to be accepted.

  • :allow_nil - when supplied, validates if it allows nil or not.

  • :message - value the test expects to find in errors.on(:attribute). Regexp, string or symbol. Default = I18n.translate('activerecord.errors.messages.accepted')

Example:

it { should validate_acceptance_of(:eula, :terms) }
it { should validate_acceptance_of(:eula, :terms, :accept => true) }


64
65
66
# File 'lib/remarkable/active_record/macros/validations/validate_acceptance_of_matcher.rb', line 64

def validate_acceptance_of(*attributes)
  ValidateAcceptanceOfMatcher.new(*attributes)
end

#validate_associated(*attributes) ⇒ Object

Ensures that the model is invalid if one of the associations given is invalid.

If an instance variable has been created in the setup named after the model being tested, then this method will use that. Otherwise, it will create a new instance to test against.

It tries to build an instance of the association by two ways. Let’s suppose a user that has many projects and you want to validate it:

it { should validate_associated(:projects) }

The first attempt to build the association would be:

@user.projects.build

If not possible, then we try:

@user.build_project

Then it tries to save the associated object. If the object can be saved if success (in this case, it allows all attributes as blank), we won’t be able to verify the validation and then an error will be raised. In such cases, you should instantiate the association before calling the matcher:

it do
  @user = User.new
  @project = @user.projects.build
  should validate_associated(:projects)
end

Or give :builder as option:

should_validate_associated :projects, :builder => proc { |user| user.projects.build }

Options:

  • :builder - a proc to build the association.

  • :message - value the test expects to find in errors.on(:attribute). Regexp, string or symbol. Default = I18n.translate('activerecord.errors.messages.invalid')

Example:

it { should validate_associated(:projects, :account) }
it { should validate_associated(:projects, :builder => proc { |user| user.projects.build }) }


162
163
164
# File 'lib/remarkable/active_record/macros/validations/validate_associated_matcher.rb', line 162

def validate_associated(*attributes)
  ValidateAssociatedMatcher.new(*attributes)
end

#validate_confirmation_of(*attributes) ⇒ Object

Ensures that the model cannot be saved if one of the attributes is not confirmed.

If an instance variable has been created in the setup named after the model being tested, then this method will use that. Otherwise, it will create a new instance to test against.

Options:

  • :message - value the test expects to find in errors.on(:attribute). Regexp, string or symbol. Default = I18n.translate('activerecord.errors.messages.confirmation')

Example:

it { should validate_confirmation_of(:email, :password) }


62
63
64
# File 'lib/remarkable/active_record/macros/validations/validate_confirmation_of_matcher.rb', line 62

def validate_confirmation_of(*attributes)
  ValidateConfirmationOfMatcher.new(*attributes)
end

#validate_exclusion_of(attribute, *good_values) ⇒ Object

Ensures that given values are not valid for the attribute. If a range is given, ensures that the attribute is not valid in the given range.

If an instance variable has been created in the setup named after the model being tested, then this method will use that. Otherwise, it will create a new instance to test against.

Note: this matcher accepts at once just one attribute to test.

Options:

  • :in - values to test exclusion.

  • :allow_nil - when supplied, validates if it allows nil or not.

  • :allow_blank - when supplied, validates if it allows blank or not.

  • :message - value the test expects to find in errors.on(:attribute). Regexp, string or symbol. Default = I18n.translate('activerecord.errors.messages.exclusion')

Example:

it { should validate_exclusion_of(:username, :in => ["admin", "user"]) }
it { should validate_exclusion_of(:age, :in => 30..60) }

should_validate_exclusion_of :username, :in => ["admin", "user"]
should_validate_exclusion_of :age, :in => 30..60


30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
# File 'lib/remarkable/active_record/macros/validations/validate_exclusion_of_matcher.rb', line 30

def validate_exclusion_of(attribute, *good_values)
  # TODO Remove this until the next comment
  options = good_values.extract_options!

  unless options.key?(:in) || good_values.empty?
    warn "[DEPRECATION] Please use validate_exclusion_of #{attribute.inspect}, :in => #{good_values[0..-2].inspect} " <<
         "instead of validate_exclusion_of #{attribute.inspect}, #{good_values[0..-2].inspect[1..-2]}."
  end

  options[:in] ||= good_values

  # From now on is what should be the actual method.
  good_values = [options.delete(:in)].flatten.compact
  good_values << options

  if good_values.first.is_a? Range
    EnsureValueInRangeMatcher.new(attribute, :exclusion, *good_values)
  else
    EnsureValueInListMatcher.new(attribute, :exclusion, *good_values)
  end
end

#validate_format_of(attribute, *good_values) ⇒ Object Also known as: allow_values_for

Ensures that the attribute can be set to the given values.

If an instance variable has been created in the setup named after the model being tested, then this method will use that. Otherwise, it will create a new instance to test against.

Note: this matcher accepts at once just one attribute to test. Note: this matcher is also aliased as “allow_values_for”

Options:

  • :allow_nil - when supplied, validates if it allows nil or not.

  • :allow_blank - when supplied, validates if it allows blank or not.

  • :message - value the test expects to find in errors.on(:attribute). Regexp, string or symbol. Default = I18n.translate('activerecord.errors.messages.invalid')

Example:

it { should validate_format_of(:isbn, "isbn 1 2345 6789 0", "ISBN 1-2345-6789-0") }
it { should_not validate_format_of(:isbn, "bad 1", "bad 2") }


26
27
28
# File 'lib/remarkable/active_record/macros/validations/validate_format_of_matcher.rb', line 26

def validate_format_of(attribute, *good_values)
  EnsureValueInListMatcher.new(attribute, :invalid, *good_values)
end

#validate_inclusion_of(attribute, *good_values) ⇒ Object

Ensures that given values are valid for the attribute. If a range is given, ensures that the attribute is valid in the given range.

If an instance variable has been created in the setup named after the model being tested, then this method will use that. Otherwise, it will create a new instance to test against.

Note: this matcher accepts at once just one attribute to test.

Options:

  • :in - values to test inclusion.

  • :allow_nil - when supplied, validates if it allows nil or not.

  • :allow_blank - when supplied, validates if it allows blank or not.

  • :message - value the test expects to find in errors.on(:attribute). Regexp, string or symbol. Default = I18n.translate('activerecord.errors.messages.inclusion')

Example:

it { should validate_inclusion_of(:size, :in => ["S", "M", "L", "XL"]) }
it { should validate_inclusion_of(:age, 18..100) }

should_validate_inclusion_of :size, :in => ["S", "M", "L", "XL"]
should_validate_inclusion_of :age, :in => 18..100


30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
# File 'lib/remarkable/active_record/macros/validations/validate_inclusion_of_matcher.rb', line 30

def validate_inclusion_of(attribute, *good_values)
  # TODO Remove this until the next comment
  options = good_values.extract_options!

  unless options.key?(:in) || good_values.empty?
    warn "[DEPRECATION] Please use validate_inclusion_of #{attribute.inspect}, :in => #{good_values[0..-2].inspect} " <<
         "instead of validate_inclusion_of #{attribute.inspect}, #{good_values[0..-2].inspect[1..-2]}."
  end

  options[:in] ||= good_values

  # From now on is what should be the actual method.
  good_values = [options.delete(:in)].flatten.compact
  good_values << options

  if good_values.first.is_a? Range
    EnsureValueInRangeMatcher.new(attribute, :inclusion, *good_values)
  else
    EnsureValueInListMatcher.new(attribute, :inclusion, *good_values)
  end
end

#validate_length_of(*attributes) ⇒ Object Also known as: validate_size_of

Validates the length of the given attributes. You have also to supply one of the following options: minimum, maximum, is or within.

If an instance variable has been created in the setup named after the model being tested, then this method will use that. Otherwise, it will create a new instance to test against.

Note: this method is also aliased as validate_size_of.

Options:

  • :minimum - The minimum size of the attribute.

  • :maximum - The maximum size of the attribute.

  • :is - The exact size of the attribute.

  • :within - A range specifying the minimum and maximum size of the attribute.

  • :in - A synonym(or alias) for :within.

  • :allow_nil - when supplied, validates if it allows nil or not.

  • :allow_blank - when supplied, validates if it allows blank or not.

  • :too_short - value the test expects to find in errors.on(:attribute) when attribute is too short. Regexp, string or symbol. Default = I18n.translate('activerecord.errors.messages.too_short') % range.first

  • :too_long - value the test expects to find in errors.on(:attribute) when attribute is too long. Regexp, string or symbol. Default = I18n.translate('activerecord.errors.messages.too_long') % range.last

  • :wrong_length - value the test expects to find in errors.on(:attribute) when attribute is the wrong length. Regexp, string or symbol. Default = I18n.translate('activerecord.errors.messages.wrong_length') % range.last

  • :message - value the test expects to find in errors.on(:attribute). When supplied overwrites :too_short, :too_long and :wrong_length. Regexp, string or symbol. Default = I18n.translate('activerecord.errors.messages.wrong_length') % value

Example:

it { should validate_length_of(:password, :within => 6..20) }
it { should validate_length_of(:password, :maximum => 20) }
it { should validate_length_of(:password, :minimum => 6) }
it { should validate_length_of(:age, :is => 18) }

it { should validate_length_of(:password).within(6..20) }
it { should validate_length_of(:password).maximum(20) }
it { should validate_length_of(:password).minimum(6) }
it { should validate_length_of(:age).is(18) }

Raises:

  • (ArgumentError)


173
174
175
176
177
178
179
180
181
182
183
184
185
# File 'lib/remarkable/active_record/macros/validations/validate_length_of_matcher.rb', line 173

def validate_length_of(*attributes)
  matcher = nil
  options = attributes.extract_options!

  [:within, :in, :maximum, :minimum, :is].each do |behavior|
    if options.key? behavior
      matcher ||= ValidateLengthOfMatcher.new(behavior, options.delete(behavior), *(attributes << options))
    end
  end

  raise ArgumentError, 'You have to give one of these options: :within, :is, :maximum or :minimum.' if matcher.nil?
  matcher
end

#validate_numericality_of(*attributes) ⇒ Object

Ensures that the given attributes accepts only numbers.

If an instance variable has been created in the setup named after the model being tested, then this method will use that. Otherwise, it will create a new instance to test against.

Options:

  • :only_integer - when supplied, checks if it accepts only integers or not

  • :odd - when supplied, checks if it accepts only odd values or not

  • :even - when supplied, checks if it accepts only even values or not

  • :equal_to - when supplied, checks if attributes are only valid when equal to given value

  • :less_than - when supplied, checks if attributes are only valid when less than given value

  • :greater_than - when supplied, checks if attributes are only valid when greater than given value

  • :less_than_or_equal_to - when supplied, checks if attributes are only valid when less than or equal to given value

  • :greater_than_or_equal_to - when supplied, checks if attributes are only valid when greater than or equal to given value

  • :message - value the test expects to find in errors.on(:attribute). Regexp, string or symbol. Default = I18n.translate('activerecord.errors.messages.not_a_number')

Example:

it { should validate_numericality_of(:age, :price) }
it { should validate_numericality_of(:age, :only_integer => true) }
it { should validate_numericality_of(:price, :only_integer => false) }
it { should validate_numericality_of(:age).only_integer }

it { should validate_numericality_of(:age).odd }
it { should validate_numericality_of(:age).even }
it { should validate_numericality_of(:age, :odd => true) }
it { should validate_numericality_of(:age, :even => true) }


215
216
217
# File 'lib/remarkable/active_record/macros/validations/validate_numericality_of_matcher.rb', line 215

def validate_numericality_of(*attributes)
  ValidateNumericalityOfMatcher.new(*attributes)
end

#validate_presence_of(*attributes) ⇒ Object

Ensures that the model cannot be saved if one of the attributes listed is not present.

If an instance variable has been created in the setup named after the model being tested, then this method will use that. Otherwise, it will create a new instance to test against.

Options:

  • :message - value the test expects to find in errors.on(:attribute). Regexp, string or symbol. Default = I18n.translate('activerecord.errors.messages.blank')

Example:

it { should validate_presence_of(:name, :phone_number) }


41
42
43
# File 'lib/remarkable/active_record/macros/validations/validate_presence_of_matcher.rb', line 41

def validate_presence_of(*attributes)
  ValidatePresenceOfMatcher.new(*attributes)
end

#validate_uniqueness_of(*attributes) ⇒ Object

Ensures that the model cannot be saved if one of the attributes listed is not unique.

Requires an existing record in the database. If you supply :allow_nil as option, you need to have in the database a record with the given attribute nil and another with the given attribute not nil. The same is required for allow_blank option.

If an instance variable has been created in the setup named after the model being tested, then this method will use that. Otherwise, it will create a new instance to test against.

Options:

  • :scope - field(s) to scope the uniqueness to.

  • :case_sensitive - the matcher look for an exact match.

  • :allow_nil - when supplied, validates if it allows nil or not.

  • :allow_blank - when supplied, validates if it allows blank or not.

  • :message - value the test expects to find in errors.on(:attribute). Regexp, string or symbol. Default = I18n.translate('activerecord.errors.messages.taken')

Examples:

it { should validate_uniqueness_of(:keyword, :username) }
it { should validate_uniqueness_of(:name, :message => "O NOES! SOMEONE STOELED YER NAME!") }
it { should validate_uniqueness_of(:email, :scope => :name, :case_sensitive => false) }
it { should validate_uniqueness_of(:address, :scope => [:first_name, :last_name]) }


206
207
208
# File 'lib/remarkable/active_record/macros/validations/validate_uniqueness_of_matcher.rb', line 206

def validate_uniqueness_of(*attributes)
  ValidateUniquenessOfMatcher.new(*attributes)
end