Defect #36226

Psych 4: Psych::DisallowedClass exception when unserializing a setting value

Added by Go MAEDA 8 days ago. Updated 6 days ago.

Status:ClosedStart date:
Priority:NormalDue date:
Assignee:Go MAEDA% Done:

0%

Category:Gems support
Target version:5.0.0
Resolution:Fixed Affected version:

Description

Psych 4.0 uses safe_load by default (see https://github.com/ruby/psych/pull/487). Due to this change, Setting#value may raise Psych::DisallowedClass exception.

$ echo gem "'psych', '~> 4.0.0'" >> Gemfile.local
$ bundle install
$ bin/rails test test/functional/settings_controller_test.rb 
Run options: --seed 45283

# Running:

...................E

Error:
SettingsControllerTest#test_post_plugin_settings:
Psych::DisallowedClass: Tried to load unspecified class: ActiveSupport::HashWithIndifferentAccess
    app/models/setting.rb:109:in `value'
    app/models/setting.rb:131:in `[]='
    app/models/setting.rb:326:in `plugin_foo='
    app/controllers/settings_controller.rb:73:in `plugin'
    lib/redmine/sudo_mode.rb:61:in `sudo_mode'
    test/functional/settings_controller_test.rb:244:in `test_post_plugin_settings'

rails test test/functional/settings_controller_test.rb:237

Related issues

Related to Redmine - Feature #36205: Ruby 3.1 support New

Associated revisions

Revision 21294
Added by Go MAEDA 6 days ago

Psych 4: Psych::DisallowedClass exception when unserializing a setting value (#36226).

Patch by Go MAEDA.

History

#1 Updated by Go MAEDA 8 days ago

#2 Updated by Go MAEDA 8 days ago

#3 Updated by Go MAEDA 8 days ago

#4 Updated by Go MAEDA 8 days ago

  • Target version set to 5.0.0

The following patch fixes the issue.

diff --git a/app/models/setting.rb b/app/models/setting.rb
index dfa054028..2b6a7a1ff 100644
--- a/app/models/setting.rb
+++ b/app/models/setting.rb
@@ -106,7 +106,8 @@ class Setting < ActiveRecord::Base
     v = read_attribute(:value)
     # Unserialize serialized settings
     if available_settings[name]['serialized'] && v.is_a?(String)
-      v = YAML::load(v)
+      # YAML.load is equivalent to YAML.safe_load in Pysch 4
+      v = YAML.respond_to?(:unsafe_load) ? YAML.unsafe_load(v) : YAML.load(v)
       v = force_utf8_strings(v)
     end
     v = v.to_sym if available_settings[name]['format'] == 'symbol' && !v.blank?

#5 Updated by Go MAEDA 6 days ago

  • Status changed from New to Closed
  • Assignee set to Go MAEDA
  • Resolution set to Fixed

Committed the fix.

Also available in: Atom PDF