diff options
Diffstat (limited to 'activemodel/test')
| -rw-r--r-- | activemodel/test/cases/attribute_methods_test.rb | 1 | ||||
| -rw-r--r-- | activemodel/test/cases/attributes_test.rb | 14 | ||||
| -rw-r--r-- | activemodel/test/cases/helper.rb | 2 | ||||
| -rw-r--r-- | activemodel/test/cases/secure_password_test.rb | 14 | ||||
| -rw-r--r-- | activemodel/test/cases/validations/acceptance_validation_test.rb | 50 | ||||
| -rw-r--r-- | activemodel/test/cases/validations/i18n_validation_test.rb | 98 | ||||
| -rw-r--r-- | activemodel/test/models/user.rb | 7 | 
7 files changed, 121 insertions, 65 deletions
diff --git a/activemodel/test/cases/attribute_methods_test.rb b/activemodel/test/cases/attribute_methods_test.rb index ebb6cc542d..4e228032c3 100644 --- a/activemodel/test/cases/attribute_methods_test.rb +++ b/activemodel/test/cases/attribute_methods_test.rb @@ -264,6 +264,5 @@ class AttributeMethodsTest < ActiveModel::TestCase      assert_equal "foo",            match.attr_name      assert_equal "attribute_test", match.target -    assert_equal "foo_test",       match.method_name    end  end diff --git a/activemodel/test/cases/attributes_test.rb b/activemodel/test/cases/attributes_test.rb index 5483fb101d..af0ddcb92f 100644 --- a/activemodel/test/cases/attributes_test.rb +++ b/activemodel/test/cases/attributes_test.rb @@ -67,6 +67,20 @@ module ActiveModel        assert_equal expected_attributes, data.attributes      end +    test "reading attribute names" do +      names = [ +        "integer_field", +        "string_field", +        "decimal_field", +        "string_with_default", +        "date_field", +        "boolean_field" +      ] + +      assert_equal names, ModelForAttributesTest.attribute_names +      assert_equal names, ModelForAttributesTest.new.attribute_names +    end +      test "nonexistent attribute" do        assert_raise ActiveModel::UnknownAttributeError do          ModelForAttributesTest.new(nonexistent: "nonexistent") diff --git a/activemodel/test/cases/helper.rb b/activemodel/test/cases/helper.rb index 138b1d1bb9..a4cb472ffc 100644 --- a/activemodel/test/cases/helper.rb +++ b/activemodel/test/cases/helper.rb @@ -25,3 +25,5 @@ class ActiveModel::TestCase < ActiveSupport::TestCase        skip message if defined?(JRUBY_VERSION)      end  end + +require_relative "../../../tools/test_common" diff --git a/activemodel/test/cases/secure_password_test.rb b/activemodel/test/cases/secure_password_test.rb index bbf443290b..0aca714bd2 100644 --- a/activemodel/test/cases/secure_password_test.rb +++ b/activemodel/test/cases/secure_password_test.rb @@ -184,6 +184,20 @@ class SecurePasswordTest < ActiveModel::TestCase      assert_nil @existing_user.password_digest    end +  test "override secure password attribute" do +    assert_nil @user.password_called + +    @user.password = "secret" + +    assert_equal "secret", @user.password +    assert_equal 1, @user.password_called + +    @user.password = "terces" + +    assert_equal "terces", @user.password +    assert_equal 2, @user.password_called +  end +    test "authenticate" do      @user.password = "secret"      @user.recovery_password = "42password" diff --git a/activemodel/test/cases/validations/acceptance_validation_test.rb b/activemodel/test/cases/validations/acceptance_validation_test.rb index 7662f996ae..72baf6e7a7 100644 --- a/activemodel/test/cases/validations/acceptance_validation_test.rb +++ b/activemodel/test/cases/validations/acceptance_validation_test.rb @@ -7,21 +7,23 @@ require "models/reply"  require "models/person"  class AcceptanceValidationTest < ActiveModel::TestCase -  def teardown -    Topic.clear_validators! +  teardown do +    self.class.send(:remove_const, :TestClass)    end    def test_terms_of_service_agreement_no_acceptance -    Topic.validates_acceptance_of(:terms_of_service) +    klass = define_test_class(Topic) +    klass.validates_acceptance_of(:terms_of_service) -    t = Topic.new("title" => "We should not be confirmed") +    t = klass.new("title" => "We should not be confirmed")      assert_predicate t, :valid?    end    def test_terms_of_service_agreement -    Topic.validates_acceptance_of(:terms_of_service) +    klass = define_test_class(Topic) +    klass.validates_acceptance_of(:terms_of_service) -    t = Topic.new("title" => "We should be confirmed", "terms_of_service" => "") +    t = klass.new("title" => "We should be confirmed", "terms_of_service" => "")      assert_predicate t, :invalid?      assert_equal ["must be accepted"], t.errors[:terms_of_service] @@ -30,9 +32,10 @@ class AcceptanceValidationTest < ActiveModel::TestCase    end    def test_eula -    Topic.validates_acceptance_of(:eula, message: "must be abided") +    klass = define_test_class(Topic) +    klass.validates_acceptance_of(:eula, message: "must be abided") -    t = Topic.new("title" => "We should be confirmed", "eula" => "") +    t = klass.new("title" => "We should be confirmed", "eula" => "")      assert_predicate t, :invalid?      assert_equal ["must be abided"], t.errors[:eula] @@ -41,9 +44,10 @@ class AcceptanceValidationTest < ActiveModel::TestCase    end    def test_terms_of_service_agreement_with_accept_value -    Topic.validates_acceptance_of(:terms_of_service, accept: "I agree.") +    klass = define_test_class(Topic) +    klass.validates_acceptance_of(:terms_of_service, accept: "I agree.") -    t = Topic.new("title" => "We should be confirmed", "terms_of_service" => "") +    t = klass.new("title" => "We should be confirmed", "terms_of_service" => "")      assert_predicate t, :invalid?      assert_equal ["must be accepted"], t.errors[:terms_of_service] @@ -52,9 +56,10 @@ class AcceptanceValidationTest < ActiveModel::TestCase    end    def test_terms_of_service_agreement_with_multiple_accept_values -    Topic.validates_acceptance_of(:terms_of_service, accept: [1, "I concur."]) +    klass = define_test_class(Topic) +    klass.validates_acceptance_of(:terms_of_service, accept: [1, "I concur."]) -    t = Topic.new("title" => "We should be confirmed", "terms_of_service" => "") +    t = klass.new("title" => "We should be confirmed", "terms_of_service" => "")      assert_predicate t, :invalid?      assert_equal ["must be accepted"], t.errors[:terms_of_service] @@ -66,9 +71,10 @@ class AcceptanceValidationTest < ActiveModel::TestCase    end    def test_validates_acceptance_of_for_ruby_class -    Person.validates_acceptance_of :karma +    klass = define_test_class(Person) +    klass.validates_acceptance_of :karma -    p = Person.new +    p = klass.new      p.karma = ""      assert_predicate p, :invalid? @@ -76,13 +82,21 @@ class AcceptanceValidationTest < ActiveModel::TestCase      p.karma = "1"      assert_predicate p, :valid? -  ensure -    Person.clear_validators!    end    def test_validates_acceptance_of_true -    Topic.validates_acceptance_of(:terms_of_service) +    klass = define_test_class(Topic) +    klass.validates_acceptance_of(:terms_of_service) -    assert_predicate Topic.new(terms_of_service: true), :valid? +    assert_predicate klass.new(terms_of_service: true), :valid?    end + +  private + +    # Acceptance validator includes anonymous module into class, which cannot +    # be cleared, so to avoid multiple inclusions we use a named subclass which +    # we can remove in teardown. +    def define_test_class(parent) +      self.class.const_set(:TestClass, Class.new(parent)) +    end  end diff --git a/activemodel/test/cases/validations/i18n_validation_test.rb b/activemodel/test/cases/validations/i18n_validation_test.rb index c94b27c23c..b7ee50832c 100644 --- a/activemodel/test/cases/validations/i18n_validation_test.rb +++ b/activemodel/test/cases/validations/i18n_validation_test.rb @@ -6,7 +6,7 @@ require "models/person"  class I18nValidationTest < ActiveModel::TestCase    def setup      Person.clear_validators! -    @person = Person.new +    @person = person_class.new      @old_load_path, @old_backend = I18n.load_path.dup, I18n.backend      I18n.load_path.clear @@ -18,7 +18,9 @@ class I18nValidationTest < ActiveModel::TestCase    end    def teardown -    Person.clear_validators! +    person_class.clear_validators! +    self.class.send(:remove_const, :Person) +    @person_stub = nil      I18n.load_path.replace @old_load_path      I18n.backend = @old_backend      I18n.backend.reload! @@ -28,14 +30,14 @@ class I18nValidationTest < ActiveModel::TestCase    def test_full_message_encoding      I18n.backend.store_translations("en", errors: {        messages: { too_short: "猫舌" } }) -    Person.validates_length_of :title, within: 3..5 +    person_class.validates_length_of :title, within: 3..5      @person.valid?      assert_equal ["Title 猫舌"], @person.errors.full_messages    end    def test_errors_full_messages_translates_human_attribute_name_for_model_attributes      @person.errors.add(:name, "not found") -    assert_called_with(Person, :human_attribute_name, ["name", default: "Name"], returns: "Person's name") do +    assert_called_with(person_class, :human_attribute_name, ["name", default: "Name"], returns: "Person's name") do        assert_equal ["Person's name not found"], @person.errors.full_messages      end    end @@ -52,7 +54,7 @@ class I18nValidationTest < ActiveModel::TestCase      I18n.backend.store_translations("en", activemodel: {        errors: { models: { person: { attributes: { name: { format: "%{message}" } } } } } }) -    person = Person.new +    person = person_class.new      assert_equal "Name cannot be blank", person.errors.full_message(:name, "cannot be blank")      assert_equal "Name test cannot be blank", person.errors.full_message(:name_test, "cannot be blank")    end @@ -63,7 +65,7 @@ class I18nValidationTest < ActiveModel::TestCase      I18n.backend.store_translations("en", activemodel: {        errors: { models: { person: { attributes: { name: { format: "%{message}" } } } } } }) -    person = Person.new +    person = person_class.new      assert_equal "cannot be blank", person.errors.full_message(:name, "cannot be blank")      assert_equal "Name test cannot be blank", person.errors.full_message(:name_test, "cannot be blank")    end @@ -74,7 +76,7 @@ class I18nValidationTest < ActiveModel::TestCase      I18n.backend.store_translations("en", activemodel: {        errors: { models: { person: { format: "%{message}" } } } }) -    person = Person.new +    person = person_class.new      assert_equal "cannot be blank", person.errors.full_message(:name, "cannot be blank")      assert_equal "cannot be blank", person.errors.full_message(:name_test, "cannot be blank")    end @@ -85,7 +87,7 @@ class I18nValidationTest < ActiveModel::TestCase      I18n.backend.store_translations("en", activemodel: {        errors: { models: { 'person/contacts/addresses': { attributes: { street: { format: "%{message}" } } } } } }) -    person = Person.new +    person = person_class.new      assert_equal "cannot be blank", person.errors.full_message(:'contacts/addresses.street', "cannot be blank")      assert_equal "Contacts/addresses country cannot be blank", person.errors.full_message(:'contacts/addresses.country', "cannot be blank")    end @@ -96,7 +98,7 @@ class I18nValidationTest < ActiveModel::TestCase      I18n.backend.store_translations("en", activemodel: {        errors: { models: { 'person/contacts/addresses': { format: "%{message}" } } } }) -    person = Person.new +    person = person_class.new      assert_equal "cannot be blank", person.errors.full_message(:'contacts/addresses.street', "cannot be blank")      assert_equal "cannot be blank", person.errors.full_message(:'contacts/addresses.country', "cannot be blank")    end @@ -107,7 +109,7 @@ class I18nValidationTest < ActiveModel::TestCase      I18n.backend.store_translations("en", activemodel: {        errors: { models: { 'person/contacts/addresses': { attributes: { street: { format: "%{message}" } } } } } }) -    person = Person.new +    person = person_class.new      assert_equal "cannot be blank", person.errors.full_message(:'contacts[0]/addresses[0].street', "cannot be blank")      assert_equal "Contacts/addresses country cannot be blank", person.errors.full_message(:'contacts[0]/addresses[0].country', "cannot be blank")    end @@ -118,7 +120,7 @@ class I18nValidationTest < ActiveModel::TestCase      I18n.backend.store_translations("en", activemodel: {        errors: { models: { 'person/contacts/addresses': { format: "%{message}" } } } }) -    person = Person.new +    person = person_class.new      assert_equal "cannot be blank", person.errors.full_message(:'contacts[0]/addresses[0].street', "cannot be blank")      assert_equal "cannot be blank", person.errors.full_message(:'contacts[0]/addresses[0].country', "cannot be blank")    end @@ -130,7 +132,7 @@ class I18nValidationTest < ActiveModel::TestCase        attributes: { 'person/contacts/addresses': { country: "Country" } }      }) -    person = Person.new +    person = person_class.new      assert_equal "Contacts/addresses street cannot be blank", person.errors.full_message(:'contacts[0]/addresses[0].street', "cannot be blank")      assert_equal "Country cannot be blank", person.errors.full_message(:'contacts[0]/addresses[0].country', "cannot be blank")    end @@ -141,7 +143,7 @@ class I18nValidationTest < ActiveModel::TestCase      I18n.backend.store_translations("en", activemodel: {        errors: { models: { 'person/contacts/addresses': { attributes: { street: { format: "%{message}" } } } } } }) -    person = Person.new +    person = person_class.new      assert_equal "Contacts[0]/addresses[0] street cannot be blank", person.errors.full_message(:'contacts[0]/addresses[0].street', "cannot be blank")      assert_equal "Contacts[0]/addresses[0] country cannot be blank", person.errors.full_message(:'contacts[0]/addresses[0].country', "cannot be blank")    end @@ -153,7 +155,7 @@ class I18nValidationTest < ActiveModel::TestCase        attributes: { 'person/contacts[0]/addresses[0]': { country: "Country" } }      }) -    person = Person.new +    person = person_class.new      assert_equal "Contacts[0]/addresses[0] street cannot be blank", person.errors.full_message(:'contacts[0]/addresses[0].street', "cannot be blank")      assert_equal "Country cannot be blank", person.errors.full_message(:'contacts[0]/addresses[0].country', "cannot be blank")    end @@ -174,7 +176,7 @@ class I18nValidationTest < ActiveModel::TestCase    COMMON_CASES.each do |name, validation_options, generate_message_options|      test "validates_confirmation_of on generated message #{name}" do -      Person.validates_confirmation_of :title, validation_options +      person_class.validates_confirmation_of :title, validation_options        @person.title_confirmation = "foo"        call = [:title_confirmation, :confirmation, generate_message_options.merge(attribute: "Title")]        assert_called_with(@person.errors, :generate_message, call) do @@ -186,7 +188,7 @@ class I18nValidationTest < ActiveModel::TestCase    COMMON_CASES.each do |name, validation_options, generate_message_options|      test "validates_acceptance_of on generated message #{name}" do -      Person.validates_acceptance_of :title, validation_options.merge(allow_nil: false) +      person_class.validates_acceptance_of :title, validation_options.merge(allow_nil: false)        call = [:title, :accepted, generate_message_options]        assert_called_with(@person.errors, :generate_message, call) do          @person.valid? @@ -197,7 +199,7 @@ class I18nValidationTest < ActiveModel::TestCase    COMMON_CASES.each do |name, validation_options, generate_message_options|      test "validates_presence_of on generated message #{name}" do -      Person.validates_presence_of :title, validation_options +      person_class.validates_presence_of :title, validation_options        call = [:title, :blank, generate_message_options]        assert_called_with(@person.errors, :generate_message, call) do          @person.valid? @@ -208,7 +210,7 @@ class I18nValidationTest < ActiveModel::TestCase    COMMON_CASES.each do |name, validation_options, generate_message_options|      test "validates_length_of for :within on generated message when too short #{name}" do -      Person.validates_length_of :title, validation_options.merge(within: 3..5) +      person_class.validates_length_of :title, validation_options.merge(within: 3..5)        call = [:title, :too_short, generate_message_options.merge(count: 3)]        assert_called_with(@person.errors, :generate_message, call) do          @person.valid? @@ -219,7 +221,7 @@ class I18nValidationTest < ActiveModel::TestCase    COMMON_CASES.each do |name, validation_options, generate_message_options|      test "validates_length_of for :too_long generated message #{name}" do -      Person.validates_length_of :title, validation_options.merge(within: 3..5) +      person_class.validates_length_of :title, validation_options.merge(within: 3..5)        @person.title = "this title is too long"        call = [:title, :too_long, generate_message_options.merge(count: 5)]        assert_called_with(@person.errors, :generate_message, call) do @@ -231,7 +233,7 @@ class I18nValidationTest < ActiveModel::TestCase    COMMON_CASES.each do |name, validation_options, generate_message_options|      test "validates_length_of for :is on generated message #{name}" do -      Person.validates_length_of :title, validation_options.merge(is: 5) +      person_class.validates_length_of :title, validation_options.merge(is: 5)        call = [:title, :wrong_length, generate_message_options.merge(count: 5)]        assert_called_with(@person.errors, :generate_message, call) do          @person.valid? @@ -242,7 +244,7 @@ class I18nValidationTest < ActiveModel::TestCase    COMMON_CASES.each do |name, validation_options, generate_message_options|      test "validates_format_of on generated message #{name}" do -      Person.validates_format_of :title, validation_options.merge(with: /\A[1-9][0-9]*\z/) +      person_class.validates_format_of :title, validation_options.merge(with: /\A[1-9][0-9]*\z/)        @person.title = "72x"        call = [:title, :invalid, generate_message_options.merge(value: "72x")]        assert_called_with(@person.errors, :generate_message, call) do @@ -254,7 +256,7 @@ class I18nValidationTest < ActiveModel::TestCase    COMMON_CASES.each do |name, validation_options, generate_message_options|      test "validates_inclusion_of on generated message #{name}" do -      Person.validates_inclusion_of :title, validation_options.merge(in: %w(a b c)) +      person_class.validates_inclusion_of :title, validation_options.merge(in: %w(a b c))        @person.title = "z"        call = [:title, :inclusion, generate_message_options.merge(value: "z")]        assert_called_with(@person.errors, :generate_message, call) do @@ -266,7 +268,7 @@ class I18nValidationTest < ActiveModel::TestCase    COMMON_CASES.each do |name, validation_options, generate_message_options|      test "validates_inclusion_of using :within on generated message #{name}" do -      Person.validates_inclusion_of :title, validation_options.merge(within: %w(a b c)) +      person_class.validates_inclusion_of :title, validation_options.merge(within: %w(a b c))        @person.title = "z"        call = [:title, :inclusion, generate_message_options.merge(value: "z")]        assert_called_with(@person.errors, :generate_message, call) do @@ -278,7 +280,7 @@ class I18nValidationTest < ActiveModel::TestCase    COMMON_CASES.each do |name, validation_options, generate_message_options|      test "validates_exclusion_of generated message #{name}" do -      Person.validates_exclusion_of :title, validation_options.merge(in: %w(a b c)) +      person_class.validates_exclusion_of :title, validation_options.merge(in: %w(a b c))        @person.title = "a"        call = [:title, :exclusion, generate_message_options.merge(value: "a")]        assert_called_with(@person.errors, :generate_message, call) do @@ -290,7 +292,7 @@ class I18nValidationTest < ActiveModel::TestCase    COMMON_CASES.each do |name, validation_options, generate_message_options|      test "validates_exclusion_of using :within generated message #{name}" do -      Person.validates_exclusion_of :title, validation_options.merge(within: %w(a b c)) +      person_class.validates_exclusion_of :title, validation_options.merge(within: %w(a b c))        @person.title = "a"        call = [:title, :exclusion, generate_message_options.merge(value: "a")]        assert_called_with(@person.errors, :generate_message, call) do @@ -302,7 +304,7 @@ class I18nValidationTest < ActiveModel::TestCase    COMMON_CASES.each do |name, validation_options, generate_message_options|      test "validates_numericality_of generated message #{name}" do -      Person.validates_numericality_of :title, validation_options +      person_class.validates_numericality_of :title, validation_options        @person.title = "a"        call = [:title, :not_a_number, generate_message_options.merge(value: "a")]        assert_called_with(@person.errors, :generate_message, call) do @@ -314,7 +316,7 @@ class I18nValidationTest < ActiveModel::TestCase    COMMON_CASES.each do |name, validation_options, generate_message_options|      test "validates_numericality_of for :only_integer on generated message #{name}" do -      Person.validates_numericality_of :title, validation_options.merge(only_integer: true) +      person_class.validates_numericality_of :title, validation_options.merge(only_integer: true)        @person.title = "0.0"        call = [:title, :not_an_integer, generate_message_options.merge(value: "0.0")]        assert_called_with(@person.errors, :generate_message, call) do @@ -326,7 +328,7 @@ class I18nValidationTest < ActiveModel::TestCase    COMMON_CASES.each do |name, validation_options, generate_message_options|      test "validates_numericality_of for :odd on generated message #{name}" do -      Person.validates_numericality_of :title, validation_options.merge(only_integer: true, odd: true) +      person_class.validates_numericality_of :title, validation_options.merge(only_integer: true, odd: true)        @person.title = 0        call = [:title, :odd, generate_message_options.merge(value: 0)]        assert_called_with(@person.errors, :generate_message, call) do @@ -338,7 +340,7 @@ class I18nValidationTest < ActiveModel::TestCase    COMMON_CASES.each do |name, validation_options, generate_message_options|      test "validates_numericality_of for :less_than on generated message #{name}" do -      Person.validates_numericality_of :title, validation_options.merge(only_integer: true, less_than: 0) +      person_class.validates_numericality_of :title, validation_options.merge(only_integer: true, less_than: 0)        @person.title = 1        call = [:title, :less_than, generate_message_options.merge(value: 1, count: 0)]        assert_called_with(@person.errors, :generate_message, call) do @@ -384,67 +386,67 @@ class I18nValidationTest < ActiveModel::TestCase    end    set_expectations_for_validation "validates_confirmation_of", :confirmation do |person, options_to_merge| -    Person.validates_confirmation_of :title, options_to_merge +    person.class.validates_confirmation_of :title, options_to_merge      person.title_confirmation = "foo"    end    set_expectations_for_validation "validates_acceptance_of", :accepted do |person, options_to_merge| -    Person.validates_acceptance_of :title, options_to_merge.merge(allow_nil: false) +    person.class.validates_acceptance_of :title, options_to_merge.merge(allow_nil: false)    end    set_expectations_for_validation "validates_presence_of", :blank do |person, options_to_merge| -    Person.validates_presence_of :title, options_to_merge +    person.class.validates_presence_of :title, options_to_merge    end    set_expectations_for_validation "validates_length_of", :too_short do |person, options_to_merge| -    Person.validates_length_of :title, options_to_merge.merge(within: 3..5) +    person.class.validates_length_of :title, options_to_merge.merge(within: 3..5)    end    set_expectations_for_validation "validates_length_of", :too_long do |person, options_to_merge| -    Person.validates_length_of :title, options_to_merge.merge(within: 3..5) +    person.class.validates_length_of :title, options_to_merge.merge(within: 3..5)      person.title = "too long"    end    set_expectations_for_validation "validates_length_of", :wrong_length do |person, options_to_merge| -    Person.validates_length_of :title, options_to_merge.merge(is: 5) +    person.class.validates_length_of :title, options_to_merge.merge(is: 5)    end    set_expectations_for_validation "validates_format_of", :invalid do |person, options_to_merge| -    Person.validates_format_of :title, options_to_merge.merge(with: /\A[1-9][0-9]*\z/) +    person.class.validates_format_of :title, options_to_merge.merge(with: /\A[1-9][0-9]*\z/)    end    set_expectations_for_validation "validates_inclusion_of", :inclusion do |person, options_to_merge| -    Person.validates_inclusion_of :title, options_to_merge.merge(in: %w(a b c)) +    person.class.validates_inclusion_of :title, options_to_merge.merge(in: %w(a b c))    end    set_expectations_for_validation "validates_exclusion_of", :exclusion do |person, options_to_merge| -    Person.validates_exclusion_of :title, options_to_merge.merge(in: %w(a b c)) +    person.class.validates_exclusion_of :title, options_to_merge.merge(in: %w(a b c))      person.title = "a"    end    set_expectations_for_validation "validates_numericality_of", :not_a_number do |person, options_to_merge| -    Person.validates_numericality_of :title, options_to_merge +    person.class.validates_numericality_of :title, options_to_merge      person.title = "a"    end    set_expectations_for_validation "validates_numericality_of", :not_an_integer do |person, options_to_merge| -    Person.validates_numericality_of :title, options_to_merge.merge(only_integer: true) +    person.class.validates_numericality_of :title, options_to_merge.merge(only_integer: true)      person.title = "1.0"    end    set_expectations_for_validation "validates_numericality_of", :odd do |person, options_to_merge| -    Person.validates_numericality_of :title, options_to_merge.merge(only_integer: true, odd: true) +    person.class.validates_numericality_of :title, options_to_merge.merge(only_integer: true, odd: true)      person.title = 0    end    set_expectations_for_validation "validates_numericality_of", :less_than do |person, options_to_merge| -    Person.validates_numericality_of :title, options_to_merge.merge(only_integer: true, less_than: 0) +    person.class.validates_numericality_of :title, options_to_merge.merge(only_integer: true, less_than: 0)      person.title = 1    end    def test_validations_with_message_symbol_must_translate      I18n.backend.store_translations "en", errors: { messages: { custom_error: "I am a custom error" } } -    Person.validates_presence_of :title, message: :custom_error +    person_class.validates_presence_of :title, message: :custom_error      @person.title = nil      @person.valid?      assert_equal ["I am a custom error"], @person.errors[:title] @@ -452,7 +454,7 @@ class I18nValidationTest < ActiveModel::TestCase    def test_validates_with_message_symbol_must_translate_per_attribute      I18n.backend.store_translations "en", activemodel: { errors: { models: { person: { attributes: { title: { custom_error: "I am a custom error" } } } } } } -    Person.validates_presence_of :title, message: :custom_error +    person_class.validates_presence_of :title, message: :custom_error      @person.title = nil      @person.valid?      assert_equal ["I am a custom error"], @person.errors[:title] @@ -460,16 +462,20 @@ class I18nValidationTest < ActiveModel::TestCase    def test_validates_with_message_symbol_must_translate_per_model      I18n.backend.store_translations "en", activemodel: { errors: { models: { person: { custom_error: "I am a custom error" } } } } -    Person.validates_presence_of :title, message: :custom_error +    person_class.validates_presence_of :title, message: :custom_error      @person.title = nil      @person.valid?      assert_equal ["I am a custom error"], @person.errors[:title]    end    def test_validates_with_message_string -    Person.validates_presence_of :title, message: "I am a custom error" +    person_class.validates_presence_of :title, message: "I am a custom error"      @person.title = nil      @person.valid?      assert_equal ["I am a custom error"], @person.errors[:title]    end + +  def person_class +    @person_stub ||= self.class.const_set(:Person, Class.new(Person)) +  end  end diff --git a/activemodel/test/models/user.rb b/activemodel/test/models/user.rb index bb1b187694..fc4a9e4334 100644 --- a/activemodel/test/models/user.rb +++ b/activemodel/test/models/user.rb @@ -10,4 +10,11 @@ class User    has_secure_password :recovery_password, validations: false    attr_accessor :password_digest, :recovery_password_digest +  attr_accessor :password_called + +  def password=(unencrypted_password) +    self.password_called ||= 0 +    self.password_called += 1 +    super +  end  end  | 
