Importazione phpBB3 fallisce con Zeitwerk::NameError sulla versione attuale di Discourse

Sto tentando importare un forum phpBB3 seguendo la guida ufficiale alla migrazione, ma lo script di importazione fallisce immediatamente con un Zeitwerk::NameError.

Ambiente

  • Versione di Discourse: v2026.2.0-latest-324 (ho provato anche i branch stable/esr)
  • Installazione: Container di importazione basato su Docker
  • Precedentemente: Ho importato con successo lo stesso forum phpBB all’inizio di gennaio 2026 senza problemi

L’Errore

/var/www/discourse/vendor/bundle/ruby/3.4.0/gems/zeitwerk-2.7.3/lib/zeitwerk/loader/callbacks.rb:31:in 'Zeitwerk::Loader::Callbacks#on_file_autoloaded': expected file /var/www/discourse/lib/freedom_patches/safe_migrations.rb to define constant FreedomPatches::SafeMigrations, but didn't (Zeitwerk::NameError)
Clicca per espandere la traccia completa dell'errore
discourse@vps116136-import-from-app:/var/www/discourse/script/import_scripts$ bundle exec ruby phpbb3.rb /shared/import/settings.yml
/var/www/discourse/vendor/bundle/ruby/3.4.0/gems/zeitwerk-2.7.3/lib/zeitwerk/loader/callbacks.rb:31:in 'Zeitwerk::Loader::Callbacks#on_file_autoloaded': expected file /var/www/discourse/lib/freedom_patches/safe_migrations.rb to define constant FreedomPatches::SafeMigrations, but didn't (Zeitwerk::NameError)

      raise Zeitwerk::NameError.new(msg, cref.cname)
      ^^^^^
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/zeitwerk-2.7.3/lib/zeitwerk/core_ext/kernel.rb:27:in 'Kernel#require'
        from /var/www/discourse/config/initializers/002-freedom_patches.rb:11:in 'block (2 levels) in <main>'
        from /var/www/discourse/config/initializers/002-freedom_patches.rb:9:in 'Array#each'
        from /var/www/discourse/config/initializers/002-freedom_patches.rb:9:in 'block in <main>'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/activesupport-8.0.4/lib/active_support/callbacks.rb:406:in 'BasicObject#instance_exec'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/activesupport-8.0.4/lib/active_support/callbacks.rb:406:in 'block in ActiveSupport::Callbacks::CallTemplate::InstanceExec0#make_lambda'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/activesupport-8.0.4/lib/active_support/callbacks.rb:178:in 'block in ActiveSupport::Callbacks::Filters::Before#call'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/activesupport-8.0.4/lib/active_support/callbacks.rb:668:in 'block (2 levels) in ActiveSupport::Callbacks::CallbackChain#default_terminator'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/activesupport-8.0.4/lib/active_support/callbacks.rb:667:in 'Kernel#catch'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/activesupport-8.0.4/lib/active_support/callbacks.rb:667:in 'block in ActiveSupport::Callbacks::CallbackChain#default_terminator'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/activesupport-8.0.4/lib/active_support/callbacks.rb:179:in 'ActiveSupport::Callbacks::Filters::Before#call'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/activesupport-8.0.4/lib/active_support/callbacks.rb:559:in 'block in ActiveSupport::Callbacks::CallbackSequence#invoke_before'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/activesupport-8.0.4/lib/active_support/callbacks.rb:559:in 'Array#each'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/activesupport-8.0.4/lib/active_support/callbacks.rb:559:in 'ActiveSupport::Callbacks::CallbackSequence#invoke_before'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/activesupport-8.0.4/lib/active_support/callbacks.rb:108:in 'ActiveSupport::Callbacks#run_callbacks'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/activesupport-8.0.4/lib/active_support/reloader.rb:96:in 'ActiveSupport::Reloader.prepare!'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/railties-8.0.4/lib/rails/application/finisher.rb:73:in 'block in <module:Finisher>'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/railties-8.0.4/lib/rails/initializable.rb:32:in 'BasicObject#instance_exec'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/railties-8.0.4/lib/rails/initializable.rb:32:in 'Rails::Initializable::Initializer#run'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/railties-8.0.4/lib/rails/initializable.rb:61:in 'block in Rails::Initializable#run_initializers'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/tsort-0.2.0/lib/tsort.rb:231:in 'block in TSort.tsort_each'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/tsort-0.2.0/lib/tsort.rb:353:in 'block (2 levels) in TSort.each_strongly_connected_component'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/tsort-0.2.0/lib/tsort.rb:434:in 'TSort.each_strongly_connected_component_from'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/tsort-0.2.0/lib/tsort.rb:352:in 'block in TSort.each_strongly_connected_component'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/tsort-0.2.0/lib/tsort.rb:350:in 'Rails::Initializable::Collection#each'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/tsort-0.2.0/lib/tsort.rb:350:in 'Method#call'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/tsort-0.2.0/lib/tsort.rb:350:in 'TSort.each_strongly_connected_component'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/tsort-0.2.0/lib/tsort.rb:229:in 'TSort#tsort_each'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/railties-8.0.4/lib/rails/initializable.rb:60:in 'Rails::Initializable#run_initializers'
        from /var/www/discourse/vendor/bundle/ruby/3.4.0/gems/railties-8.0.4/lib/rails/application.rb:444:in 'Rails::Application#initialize!'
        from /var/www/discourse/config/environment.rb:7:in '<top (required)>'
        from /var/www/discourse/script/import_scripts/base.rb:16:in 'Kernel#require_relative'
        from /var/www/discourse/script/import_scripts/base.rb:16:in '<top (required)>'
        from /var/www/discourse/script/import_scripts/phpbb3/support/settings.rb:5:in 'Kernel#require_relative'
        from /var/www/discourse/script/import_scripts/phpbb3/support/settings.rb:5:in '<top (required)>'
        from phpbb3.rb:17:in 'Kernel#require_relative'
        from phpbb3.rb:17:in '<module:PhpBB3>'
        from phpbb3.rb:16:in '<module:ImportScripts>'
        from phpbb3.rb:15:in '<main>'

Ciò che ho provato

  1. Diverse versioni di Discourse: Testato con i branch latest, stable e esr - tutti falliscono con lo stesso errore
  2. Diversi ambienti Rails: Provato RAILS_ENV=production e RAILS_ENV=development
  3. Nuove build del container: Distrutto e ricostruito il container di importazione più volte
  4. Bundle install: Aggiornato le dipendenze con bundle install

Analisi della Causa Principale

Il file /var/www/discourse/lib/freedom_patches/safe_migrations.rb definisce la costante SafeMigrations solo quando RAILS_ENV != "production":

if ENV["RAILS_ENV"] != "production"
  require_dependency "migration/safe_migrate"
  Migration::SafeMigrate.patch_active_record!
end

Tuttavia, l’initializer /var/www/discourse/config/initializers/002-freedom_patches.rb tenta di richiedere questo file incondizionatamente, causando l’errore Zeitwerk in modalità produzione.

Domande

  1. Qualcun altro ha riscontrato questo problema con le versioni recenti di Discourse?
  2. Esiste una soluzione alternativa o una correzione nota?
  3. Quale versione di Discourse è attualmente consigliata per le importazioni da phpBB?

Il fatto che abbia funzionato a gennaio ma fallisca ora suggerisce una recente modifica che rompe la compatibilità nel core di Discourse. Qualsiasi indicazione sarebbe molto apprezzata!