From 84f6eafbb95efdf5e5f52e168c9efbd35c0aad46 Mon Sep 17 00:00:00 2001 From: Martin Date: Wed, 2 Feb 2022 14:12:26 +0100 Subject: [PATCH] Fix frozen string in validatable, use multiline string instead. Expand tests to check for the actual validatable exception message This was raising a `FrozenError` on Ruby < 3 where interpolated strings were considered frozen. This [changed in Ruby 3], since such strings are dynamic there's no point in freezing them by default. The test wasn't catching this because `FrozenError` actually inherits from `RuntimeError`: >> FrozenError.ancestors => [FrozenError, RuntimeError, StandardError, Exception, Object ...] So the exception check passed. Now we're also checking for the error message to ensure it raised the exception we really expected there. Closes #5465 [changed in Ruby 3] https://bugs.ruby-lang.org/issues/17104 --- CHANGELOG.md | 2 ++ lib/devise/models/validatable.rb | 2 +- test/models/validatable_test.rb | 5 ++++- 3 files changed, 7 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 94fafa5f4b..34ef572f9e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,7 @@ ### Unreleased +* bug fixes + * Fix frozen string exception in validatable. [#5563](https://github.com/heartcombo/devise/pull/5563) [@mameier](https://github.com/mameier) ### 4.9.0 - 2023-02-17 diff --git a/lib/devise/models/validatable.rb b/lib/devise/models/validatable.rb index 8f600a8c01..5a190a7c36 100644 --- a/lib/devise/models/validatable.rb +++ b/lib/devise/models/validatable.rb @@ -47,7 +47,7 @@ def self.assert_validations_api!(base) #:nodoc: unavailable_validations = VALIDATIONS.select { |v| !base.respond_to?(v) } unless unavailable_validations.empty? - raise "Could not use :validatable module since #{base} does not respond " << + raise "Could not use :validatable module since #{base} does not respond " \ "to the following methods: #{unavailable_validations.to_sentence}." end end diff --git a/test/models/validatable_test.rb b/test/models/validatable_test.rb index f96cfa9182..d3b5c9dc00 100644 --- a/test/models/validatable_test.rb +++ b/test/models/validatable_test.rb @@ -110,9 +110,12 @@ class ValidatableTest < ActiveSupport::TestCase end test 'should not be included in objects with invalid API' do - assert_raise RuntimeError do + exception = assert_raise RuntimeError do Class.new.send :include, Devise::Models::Validatable end + + expected_message = /Could not use :validatable module since .* does not respond to the following methods: validates_presence_of.*/ + assert_match expected_message, exception.message end test 'required_fields should be an empty array' do