diff --git a/Gemfile b/Gemfile index 7422505d15..d02b160685 100644 --- a/Gemfile +++ b/Gemfile @@ -79,7 +79,7 @@ # the new version. It is always preferable to upgrade our code. source 'https://rubygems.org' -gem 'rails', '~> 7.0.8' +gem 'rails', '~> 7.1.5.1' gem 'pg', '~> 1.5.9' diff --git a/Gemfile.lock b/Gemfile.lock index 7b1e353481..3336e03989 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -39,7 +39,7 @@ PATH flipper (~> 1.3.2) flipper-active_record (~> 1.3.2) mime-types (< 4.0.0) - rails (>= 7.0.4, < 8.1.0) + rails (>= 7.1.5.1, < 7.2.0) PATH remote: gems/excel_analyzer @@ -54,76 +54,88 @@ PATH GEM remote: https://rubygems.org/ specs: - actioncable (7.0.8.7) - actionpack (= 7.0.8.7) - activesupport (= 7.0.8.7) + actioncable (7.1.5.1) + actionpack (= 7.1.5.1) + activesupport (= 7.1.5.1) nio4r (~> 2.0) websocket-driver (>= 0.6.1) - actionmailbox (7.0.8.7) - actionpack (= 7.0.8.7) - activejob (= 7.0.8.7) - activerecord (= 7.0.8.7) - activestorage (= 7.0.8.7) - activesupport (= 7.0.8.7) + zeitwerk (~> 2.6) + actionmailbox (7.1.5.1) + actionpack (= 7.1.5.1) + activejob (= 7.1.5.1) + activerecord (= 7.1.5.1) + activestorage (= 7.1.5.1) + activesupport (= 7.1.5.1) mail (>= 2.7.1) net-imap net-pop net-smtp - actionmailer (7.0.8.7) - actionpack (= 7.0.8.7) - actionview (= 7.0.8.7) - activejob (= 7.0.8.7) - activesupport (= 7.0.8.7) + actionmailer (7.1.5.1) + actionpack (= 7.1.5.1) + actionview (= 7.1.5.1) + activejob (= 7.1.5.1) + activesupport (= 7.1.5.1) mail (~> 2.5, >= 2.5.4) net-imap net-pop net-smtp - rails-dom-testing (~> 2.0) - actionpack (7.0.8.7) - actionview (= 7.0.8.7) - activesupport (= 7.0.8.7) - rack (~> 2.0, >= 2.2.4) + rails-dom-testing (~> 2.2) + actionpack (7.1.5.1) + actionview (= 7.1.5.1) + activesupport (= 7.1.5.1) + nokogiri (>= 1.8.5) + racc + rack (>= 2.2.4) + rack-session (>= 1.0.1) rack-test (>= 0.6.3) - rails-dom-testing (~> 2.0) - rails-html-sanitizer (~> 1.0, >= 1.2.0) - actiontext (7.0.8.7) - actionpack (= 7.0.8.7) - activerecord (= 7.0.8.7) - activestorage (= 7.0.8.7) - activesupport (= 7.0.8.7) + rails-dom-testing (~> 2.2) + rails-html-sanitizer (~> 1.6) + actiontext (7.1.5.1) + actionpack (= 7.1.5.1) + activerecord (= 7.1.5.1) + activestorage (= 7.1.5.1) + activesupport (= 7.1.5.1) globalid (>= 0.6.0) nokogiri (>= 1.8.5) - actionview (7.0.8.7) - activesupport (= 7.0.8.7) + actionview (7.1.5.1) + activesupport (= 7.1.5.1) builder (~> 3.1) - erubi (~> 1.4) - rails-dom-testing (~> 2.0) - rails-html-sanitizer (~> 1.1, >= 1.2.0) + erubi (~> 1.11) + rails-dom-testing (~> 2.2) + rails-html-sanitizer (~> 1.6) active_model_otp (2.3.4) activemodel rotp (~> 6.3.0) - activejob (7.0.8.7) - activesupport (= 7.0.8.7) + activejob (7.1.5.1) + activesupport (= 7.1.5.1) globalid (>= 0.3.6) activejob-uniqueness (0.4.0) activejob (>= 4.2, < 8.1) redlock (>= 2.0, < 3) - activemodel (7.0.8.7) - activesupport (= 7.0.8.7) - activerecord (7.0.8.7) - activemodel (= 7.0.8.7) - activesupport (= 7.0.8.7) - activestorage (7.0.8.7) - actionpack (= 7.0.8.7) - activejob (= 7.0.8.7) - activerecord (= 7.0.8.7) - activesupport (= 7.0.8.7) + activemodel (7.1.5.1) + activesupport (= 7.1.5.1) + activerecord (7.1.5.1) + activemodel (= 7.1.5.1) + activesupport (= 7.1.5.1) + timeout (>= 0.4.0) + activestorage (7.1.5.1) + actionpack (= 7.1.5.1) + activejob (= 7.1.5.1) + activerecord (= 7.1.5.1) + activesupport (= 7.1.5.1) marcel (~> 1.0) - mini_mime (>= 1.1.0) - activesupport (7.0.8.7) + activesupport (7.1.5.1) + base64 + benchmark (>= 0.3) + bigdecimal concurrent-ruby (~> 1.0, >= 1.0.2) + connection_pool (>= 2.2.5) + drb i18n (>= 1.6, < 2) + logger (>= 1.4.2) minitest (>= 5.1) + mutex_m + securerandom (>= 0.3) tzinfo (~> 2.0) addressable (2.8.7) public_suffix (>= 2.0.2, < 7.0) @@ -149,6 +161,7 @@ GEM aws-eventstream (~> 1, >= 1.0.2) base64 (0.2.0) bcrypt (3.1.20) + benchmark (0.4.0) bigdecimal (3.1.8) bindex (0.8.1) bootstrap-sass (2.3.2.2) @@ -190,6 +203,7 @@ GEM digest-crc (0.6.5) rake (>= 12.0.0, < 14.0.0) docile (1.4.0) + drb (2.2.1) erubi (1.13.1) execjs (2.9.1) factory_bot (6.5.0) @@ -293,6 +307,10 @@ GEM actionpack (>= 6.0.0) activesupport (>= 6.0.0) railties (>= 6.0.0) + io-console (0.8.0) + irb (1.14.3) + rdoc (>= 4.0.0) + reline (>= 0.4.2) iso_country_codes (0.7.8) jmespath (1.6.2) jquery-rails (4.6.0) @@ -389,29 +407,37 @@ GEM pry (0.15.2) coderay (~> 1.1) method_source (~> 1.0) + psych (5.2.2) + date + stringio public_suffix (6.0.1) puma (6.5.0) nio4r (~> 2.0) racc (1.8.1) rack (2.2.10) + rack-session (1.0.2) + rack (< 3) rack-test (2.1.0) rack (>= 1.3) rack-utf8_sanitizer (1.10.1) rack (>= 1.0, < 4.0) - rails (7.0.8.7) - actioncable (= 7.0.8.7) - actionmailbox (= 7.0.8.7) - actionmailer (= 7.0.8.7) - actionpack (= 7.0.8.7) - actiontext (= 7.0.8.7) - actionview (= 7.0.8.7) - activejob (= 7.0.8.7) - activemodel (= 7.0.8.7) - activerecord (= 7.0.8.7) - activestorage (= 7.0.8.7) - activesupport (= 7.0.8.7) + rackup (1.0.1) + rack (< 3) + webrick + rails (7.1.5.1) + actioncable (= 7.1.5.1) + actionmailbox (= 7.1.5.1) + actionmailer (= 7.1.5.1) + actionpack (= 7.1.5.1) + actiontext (= 7.1.5.1) + actionview (= 7.1.5.1) + activejob (= 7.1.5.1) + activemodel (= 7.1.5.1) + activerecord (= 7.1.5.1) + activestorage (= 7.1.5.1) + activesupport (= 7.1.5.1) bundler (>= 1.15.0) - railties (= 7.0.8.7) + railties (= 7.1.5.1) rails-controller-testing (1.0.5) actionpack (>= 5.0.1.rc1) actionview (>= 5.0.1.rc1) @@ -426,15 +452,18 @@ GEM rails-i18n (7.0.10) i18n (>= 0.7, < 2) railties (>= 6.0.0, < 8) - railties (7.0.8.7) - actionpack (= 7.0.8.7) - activesupport (= 7.0.8.7) - method_source + railties (7.1.5.1) + actionpack (= 7.1.5.1) + activesupport (= 7.1.5.1) + irb + rackup (>= 1.0.0) rake (>= 12.2) - thor (~> 1.0) - zeitwerk (~> 2.5) + thor (~> 1.0, >= 1.2.2) + zeitwerk (~> 2.6) rainbow (3.1.1) rake (13.2.1) + rdoc (6.10.0) + psych (>= 4.0.0) recaptcha (5.18.0) redcarpet (3.6.0) redis (4.8.1) @@ -443,6 +472,8 @@ GEM redlock (2.0.6) redis-client (>= 0.14.1, < 1.0.0) regexp_parser (2.10.0) + reline (0.6.0) + io-console (~> 0.5) representable (3.2.0) declarative (< 0.1.0) trailblazer-option (>= 0.1.1, < 0.2.0) @@ -511,6 +542,7 @@ GEM sprockets-rails (>= 2.0, < 4.0) tilt (>= 1.1, < 3) secure_headers (7.0.0) + securerandom (0.4.1) sidekiq (6.5.12) connection_pool (>= 2.2.5, < 3) rack (~> 2.0) @@ -541,6 +573,7 @@ GEM statistics2 (0.54) stimulus-rails (1.3.4) railties (>= 6.0.0) + stringio (3.1.2) stripe (11.7.0) stripe-ruby-mock (4.0.0) dante (>= 0.2.0) @@ -578,7 +611,9 @@ GEM addressable (>= 2.8.0) crack (>= 0.3.2) hashdiff (>= 0.4.0, < 2.0.0) - websocket-driver (0.7.6) + webrick (1.9.1) + websocket-driver (0.7.7) + base64 websocket-extensions (>= 0.1.0) websocket-extensions (0.1.5) will_paginate (4.0.1) @@ -658,7 +693,7 @@ DEPENDENCIES puma (~> 6.5.0) rack (~> 2.2.10) rack-utf8_sanitizer (~> 1.10.1) - rails (~> 7.0.8) + rails (~> 7.1.5.1) rails-controller-testing rails-i18n (~> 7.0.10) recaptcha (~> 5.18.0) diff --git a/app/models/mail_server_log.rb b/app/models/mail_server_log.rb index 0e9ceff179..3f4f148e6c 100644 --- a/app/models/mail_server_log.rb +++ b/app/models/mail_server_log.rb @@ -21,7 +21,7 @@ class MailServerLog < ApplicationRecord # `serialize` needs to be called before all other ActiveRecord code. # See http://stackoverflow.com/a/15610692/387558 - serialize :delivery_status, DeliveryStatusSerializer + serialize :delivery_status, coder: DeliveryStatusSerializer belongs_to :info_request, inverse_of: :mail_server_logs, diff --git a/bin/rails b/bin/rails index 6fb4e4051c..efc0377492 100755 --- a/bin/rails +++ b/bin/rails @@ -1,4 +1,4 @@ #!/usr/bin/env ruby -APP_PATH = File.expand_path('../config/application', __dir__) +APP_PATH = File.expand_path("../config/application", __dir__) require_relative "../config/boot" require "rails/commands" diff --git a/bin/setup b/bin/setup index 57923026c4..3cd5a9d780 100755 --- a/bin/setup +++ b/bin/setup @@ -2,10 +2,10 @@ require "fileutils" # path to your application root. -APP_ROOT = File.expand_path('..', __dir__) +APP_ROOT = File.expand_path("..", __dir__) def system!(*args) - system(*args) || abort("\n== Command #{args} failed ==") + system(*args, exception: true) end FileUtils.chdir APP_ROOT do @@ -13,21 +13,21 @@ FileUtils.chdir APP_ROOT do # This script is idempotent, so that you can run it at any time and get an expectable outcome. # Add necessary setup steps to this file. - puts '== Installing dependencies ==' - system! 'gem install bundler --conservative' - system('bundle check') || system!('bundle install') + puts "== Installing dependencies ==" + system! "gem install bundler --conservative" + system("bundle check") || system!("bundle install") # puts "\n== Copying sample files ==" - # unless File.exist?('config/database.yml') - # FileUtils.cp 'config/database.yml.sample', 'config/database.yml' + # unless File.exist?("config/database.yml") + # FileUtils.cp "config/database.yml.sample", "config/database.yml" # end puts "\n== Preparing database ==" - system! 'bin/rails db:prepare' + system! "bin/rails db:prepare" puts "\n== Removing old logs and tempfiles ==" - system! 'bin/rails log:clear tmp:clear' + system! "bin/rails log:clear tmp:clear" puts "\n== Restarting application server ==" - system! 'bin/rails restart' + system! "bin/rails restart" end diff --git a/config/application.rb b/config/application.rb index 6c4d965b5b..83ed87ce74 100644 --- a/config/application.rb +++ b/config/application.rb @@ -12,7 +12,6 @@ require "action_text/engine" require "action_view/railtie" # require "action_cable/engine" -require "sprockets/railtie" # require "rails/test_unit/railtie" require File.dirname(__FILE__) + '/../lib/configuration' @@ -24,6 +23,29 @@ module Alaveteli class Application < Rails::Application + # Initialize configuration defaults for originally generated Rails version. + config.load_defaults 7.1 + + # Disable new framework default has_many_inversing breaks some specs due to + # an apparent regression in Rails + config.active_record.has_many_inversing = false # 6.1 + + # Please, add to the `ignore` list any other `lib` subdirectories that do + # not contain `.rb` files, or that should not be reloaded or eager loaded. + # Common ones are `templates`, `generators`, or `middleware`, for example. + config.autoload_lib( + ignore: %w( + acts_as_xapian + assets + core_ext + custom_cops + generators + has_tag_string + tasks + themes + ) + ) + # Configuration for the application, engines, and railties goes here. # # These settings can be overridden in specific environments using the files @@ -31,16 +53,9 @@ class Application < Rails::Application # # config.time_zone = "Central Time (US & Canada)" # config.eager_load_paths << Rails.root.join("extras") - config.load_defaults 7.0 - config.autoloader = :zeitwerk - # Enable new framework defaults configurations for later Rails versions - # preventing deprecation warnings - config.active_storage.replace_on_assign_to_many = true # 7.1 - - # Disable new framework default has_many_inversing breaks some specs due to - # an apparent regression in Rails - config.active_record.has_many_inversing = false # 6.1 + # Don't generate system test files. + config.generators.system_tests = nil # The default locale is :en and all translations from config/locales/*.rb,yml are auto loaded. # config.i18n.load_path += Dir[Rails.root.join('my', 'locales', '*.{rb,yml}').to_s] @@ -89,8 +104,6 @@ class Application < Rails::Application config.autoload_paths << "#{Rails.root}/app/controllers/concerns" config.autoload_paths << "#{Rails.root}/app/models/concerns" - config.enable_dependency_loading = true - # See Rails::Configuration for more options ENV['RECAPTCHA_SITE_KEY'] = AlaveteliConfiguration.recaptcha_site_key ENV['RECAPTCHA_SECRET_KEY'] = AlaveteliConfiguration.recaptcha_secret_key diff --git a/config/boot.rb b/config/boot.rb index 662856d3b3..65a0c8720c 100644 --- a/config/boot.rb +++ b/config/boot.rb @@ -1,4 +1,4 @@ -ENV['BUNDLE_GEMFILE'] ||= File.expand_path('../Gemfile', __dir__) +ENV["BUNDLE_GEMFILE"] ||= File.expand_path("../Gemfile", __dir__) require "bundler/setup" # Set up gems listed in the Gemfile. diff --git a/config/environments/development.rb b/config/environments/development.rb index e564d070f1..0fff5f0a6e 100644 --- a/config/environments/development.rb +++ b/config/environments/development.rb @@ -6,7 +6,7 @@ # In the development environment your application's code is reloaded any time # it changes. This slows down response time but is perfect for development # since you don't have to restart the web server when you make code changes. - config.cache_classes = false + config.enable_reloading = true # Do not eager load code on boot. config.eager_load = false @@ -14,15 +14,18 @@ # Show full error reports. config.consider_all_requests_local = true + # Enable server timing + config.server_timing = true + # Enable/disable caching. By default caching is disabled. # Run rails dev:cache to toggle caching. - if Rails.root.join('tmp', 'caching-dev.txt').exist? + if Rails.root.join("tmp/caching-dev.txt").exist? config.action_controller.perform_caching = true config.action_controller.enable_fragment_cache_logging = true config.cache_store = :memory_store config.public_file_server.headers = { - 'Cache-Control' => "public, max-age=#{2.days.to_i}" + "Cache-Control" => "public, max-age=#{2.days.to_i}" } else config.action_controller.perform_caching = false @@ -30,6 +33,9 @@ config.cache_store = :null_store end + # Store uploaded files on the local file system (see config/storage.yml for options). + config.active_storage.service = :local + # Don't care if the mailer can't send. config.action_mailer.raise_delivery_errors = false @@ -50,10 +56,8 @@ # Highlight code that triggered database queries in logs. config.active_record.verbose_query_logs = true - # Debug mode disables concatenation and preprocessing of assets. - # This option may cause significant delays in view rendering with a large - # number of complex assets. - config.assets.debug = ENV.key?('ASSETS_DEBUG') || false + # Highlight code that enqueued background job in logs. + config.active_job.verbose_enqueue_logs = true # Suppress logger output for asset requests. config.assets.quiet = true @@ -64,8 +68,8 @@ # Annotate rendered view with file names. # config.action_view.annotate_rendered_view_with_filenames = true - # Uncomment if you wish to allow Action Cable access from any origin. - # config.action_cable.disable_request_forgery_protection = true + # Raise error when a before_action's only/except options reference missing actions + config.action_controller.raise_on_missing_callback_actions = true # CUSTOM CONFIGURATION # @@ -73,15 +77,9 @@ # to make Rails upgrades easier. # ---------------------------------------------------------------- - if Rails.version < '7.1.0' - config.action_mailer.preview_path = Rails.root.join( - 'spec', 'mailers', 'previews' - ) - else - config.action_mailer.preview_paths = [ - Rails.root.join('spec', 'mailers', 'previews') - ] - end + config.action_mailer.preview_paths = [ + Rails.root.join('spec', 'mailers', 'previews') + ] # Set LOG_LEVEL in the environment to a valid log level to temporarily run the # application with a non-default setting. diff --git a/config/environments/production.rb b/config/environments/production.rb index dc04044cf5..02e60346d2 100644 --- a/config/environments/production.rb +++ b/config/environments/production.rb @@ -4,7 +4,7 @@ # Settings specified here will take precedence over those in config/application.rb. # Code is not reloaded between requests. - config.cache_classes = true + config.enable_reloading = false # Eager load code on boot. This eager loads most of Rails and # your application in memory, allowing both threaded web servers @@ -13,45 +13,57 @@ config.eager_load = true # Full error reports are disabled and caching is turned on. - config.consider_all_requests_local = false + config.consider_all_requests_local = false config.action_controller.perform_caching = true - # Ensures that a master key has been made available in either ENV["RAILS_MASTER_KEY"] - # or in config/master.key. This key is used to decrypt credentials (and other encrypted files). + # Ensures that a master key has been made available in ENV["RAILS_MASTER_KEY"], config/master.key, or an environment + # key such as config/credentials/production.key. This key is used to decrypt credentials (and other encrypted files). # config.require_master_key = true - # Disable serving static files from the `/public` folder by default since - # Apache or NGINX already handles this. - config.public_file_server.enabled = ENV['RAILS_SERVE_STATIC_FILES'].present? + # Disable serving static files from `public/`, relying on NGINX/Apache to do so instead. + # config.public_file_server.enabled = false # Compress CSS using a preprocessor. # config.assets.css_compressor = :sass - # Do not fallback to assets pipeline if a precompiled asset is missed. + # Do not fall back to assets pipeline if a precompiled asset is missed. config.assets.compile = false # Enable serving of images, stylesheets, and JavaScripts from an asset server. - # config.asset_host = 'http://assets.example.com' + # config.asset_host = "http://assets.example.com" # Specifies the header that your server uses for sending files. - # config.action_dispatch.x_sendfile_header = 'X-Sendfile' # for Apache - # config.action_dispatch.x_sendfile_header = 'X-Accel-Redirect' # for NGINX + # config.action_dispatch.x_sendfile_header = "X-Sendfile" # for Apache + # config.action_dispatch.x_sendfile_header = "X-Accel-Redirect" # for NGINX + + # Store uploaded files on the local file system (see config/storage.yml for options). + config.active_storage.service = :local + + # Assume all access to the app is happening through a SSL-terminating reverse proxy. + # Can be used together with config.force_ssl for Strict-Transport-Security and secure cookies. + # config.assume_ssl = true # Force all access to the app over SSL, use Strict-Transport-Security, and use secure cookies. config.force_ssl = AlaveteliConfiguration.force_ssl - # Include generic and useful information about system operation, but avoid logging too much - # information to avoid inadvertent exposure of personally identifiable information (PII). - config.log_level = ENV.fetch('LOG_LEVEL', :info) + # Log to STDOUT by default + config.logger = ActiveSupport::Logger.new(STDOUT) + .tap { |logger| logger.formatter = ::Logger::Formatter.new } + .then { |logger| ActiveSupport::TaggedLogging.new(logger) } # Prepend all log lines with the following tags. config.log_tags = [ :request_id ] + # "info" includes generic and useful information about system operation, but avoids logging too much + # information to avoid inadvertent exposure of personally identifiable information (PII). If you + # want to log everything, set the level to "debug". + config.log_level = ENV.fetch("RAILS_LOG_LEVEL", "info") + # Use a different cache store in production. # config.cache_store = :mem_cache_store # Use a real queuing backend for Active Job (and separate queues per environment). - # config.active_job.queue_adapter = :resque + # config.active_job.queue_adapter = :resque # config.active_job.queue_name_prefix = "alaveteli_production" config.action_mailer.perform_caching = false @@ -64,51 +76,19 @@ # the I18n.default_locale when a translation cannot be found). config.i18n.fallbacks = true - # Send deprecation notices to registered listeners. - config.active_support.deprecation = :notify - - # Log disallowed deprecations. - config.active_support.disallowed_deprecation = :log - - # Tell Active Support which deprecation messages to disallow. - config.active_support.disallowed_deprecation_warnings = [] - - # Use default logging formatter so that PID and timestamp are not suppressed. - config.log_formatter = ::Logger::Formatter.new - - # Use a different logger for distributed setups. - # require "syslog/logger" - # config.logger = ActiveSupport::TaggedLogging.new(Syslog::Logger.new 'app-name') - - if ENV["RAILS_LOG_TO_STDOUT"].present? - logger = ActiveSupport::Logger.new(STDOUT) - logger.formatter = config.log_formatter - config.logger = ActiveSupport::TaggedLogging.new(logger) - end + # Don't log any deprecations. + config.active_support.report_deprecations = false # Do not dump schema after migrations. config.active_record.dump_schema_after_migration = false - # Inserts middleware to perform automatic connection switching. - # The `database_selector` hash is used to pass options to the DatabaseSelector - # middleware. The `delay` is used to determine how long to wait after a write - # to send a subsequent read to the primary. - # - # The `database_resolver` class is used by the middleware to determine which - # database is appropriate to use based on the time delay. - # - # The `database_resolver_context` class is used by the middleware to set - # timestamps for the last write to the primary. The resolver uses the context - # class timestamps to determine how long to wait before reading from the - # replica. - # - # By default Rails will store a last write timestamp in the session. The - # DatabaseSelector middleware is designed as such you can define your own - # strategy for connection switching and pass that into the middleware through - # these configuration options. - # config.active_record.database_selector = { delay: 2.seconds } - # config.active_record.database_resolver = ActiveRecord::Middleware::DatabaseSelector::Resolver - # config.active_record.database_resolver_context = ActiveRecord::Middleware::DatabaseSelector::Resolver::Session + # Enable DNS rebinding protection and other `Host` header attacks. + # config.hosts = [ + # "example.com", # Allow requests from example.com + # /.*\.example\.com/ # Allow requests from subdomains like `www.example.com` + # ] + # Skip DNS rebinding protection for the default health check endpoint. + # config.host_authorization = { exclude: ->(request) { request.path == "/up" } } # CUSTOM CONFIGURATION # diff --git a/config/environments/test.rb b/config/environments/test.rb index c3116c26c5..4d7a99baf1 100644 --- a/config/environments/test.rb +++ b/config/environments/test.rb @@ -8,29 +8,28 @@ Rails.application.configure do # Settings specified here will take precedence over those in config/application.rb. - config.cache_classes = true + # While tests run files are not watched, reloading is not necessary. + config.enable_reloading = false - # Do not eager load code on boot. This avoids loading your whole application - # just for the purpose of running a single test. If you are using a tool that - # preloads Rails for running tests, you may have to set it to true. - config.eager_load = false + # Eager loading loads your entire application. When running a single test locally, + # this is usually not necessary, and can slow down your test suite. However, it's + # recommended that you enable it in continuous integration systems to ensure eager + # loading is working properly before deploying your code. + config.eager_load = ENV["CI"].present? # Configure public file server for tests with Cache-Control for performance. config.public_file_server.enabled = true config.public_file_server.headers = { - 'Cache-Control' => "public, max-age=#{1.hour.to_i}" + "Cache-Control" => "public, max-age=#{1.hour.to_i}" } # Show full error reports and disable caching. - config.consider_all_requests_local = true + config.consider_all_requests_local = true config.action_controller.perform_caching = false config.cache_store = :null_store - # Use inline processing for Active Job - config.active_job.queue_adapter = :test - - # Raise exceptions instead of rendering exception templates. - config.action_dispatch.show_exceptions = false + # Render exception templates for rescuable exceptions and raise for other exceptions. + config.action_dispatch.show_exceptions = :rescuable # Disable request forgery protection in test environment. config.action_controller.allow_forgery_protection = false @@ -60,6 +59,9 @@ # Annotate rendered view with file names. # config.action_view.annotate_rendered_view_with_filenames = true + # Raise error when a before_action's only/except options reference missing actions + config.action_controller.raise_on_missing_callback_actions = true + # CUSTOM CONFIGURATION # # Always place custom environment config at the bottom of the file diff --git a/config/initializers/assets.rb b/config/initializers/assets.rb index 82c9ad3fcb..2fff5fe8ca 100644 --- a/config/initializers/assets.rb +++ b/config/initializers/assets.rb @@ -1,7 +1,7 @@ # Be sure to restart your server when you modify this file. # Version of your assets, change this if you want to expire all your assets. -Rails.application.config.assets.version = '1.0' +Rails.application.config.assets.version = "1.0" # Add additional assets to the asset load path. # Rails.application.config.assets.paths << Emoji.images_path diff --git a/config/initializers/content_security_policy.rb b/config/initializers/content_security_policy.rb index 41c43016f1..b3076b38fe 100644 --- a/config/initializers/content_security_policy.rb +++ b/config/initializers/content_security_policy.rb @@ -1,28 +1,25 @@ # Be sure to restart your server when you modify this file. -# Define an application-wide content security policy -# For further information see the following documentation -# https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Content-Security-Policy +# Define an application-wide content security policy. +# See the Securing Rails Applications Guide for more information: +# https://guides.rubyonrails.org/security.html#content-security-policy-header -# Rails.application.config.content_security_policy do |policy| -# policy.default_src :self, :https -# policy.font_src :self, :https, :data -# policy.img_src :self, :https, :data -# policy.object_src :none -# policy.script_src :self, :https -# policy.style_src :self, :https - -# # Specify URI for violation reports -# # policy.report_uri "/csp-violation-report-endpoint" +# Rails.application.configure do +# config.content_security_policy do |policy| +# policy.default_src :self, :https +# policy.font_src :self, :https, :data +# policy.img_src :self, :https, :data +# policy.object_src :none +# policy.script_src :self, :https +# policy.style_src :self, :https +# # Specify URI for violation reports +# # policy.report_uri "/csp-violation-report-endpoint" +# end +# +# # Generate session nonces for permitted importmap, inline scripts, and inline styles. +# config.content_security_policy_nonce_generator = ->(request) { request.session.id.to_s } +# config.content_security_policy_nonce_directives = %w(script-src style-src) +# +# # Report violations without enforcing the policy. +# # config.content_security_policy_report_only = true # end - -# If you are using UJS then enable automatic nonce generation -# Rails.application.config.content_security_policy_nonce_generator = -> request { SecureRandom.base64(16) } - -# Set the nonce only to specific directives -# Rails.application.config.content_security_policy_nonce_directives = %w(script-src) - -# Report CSP violations to a specified URI -# For further information see the following documentation: -# https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Content-Security-Policy-Report-Only -# Rails.application.config.content_security_policy_report_only = true diff --git a/config/initializers/filter_parameter_logging.rb b/config/initializers/filter_parameter_logging.rb index 656e8ab03e..7b5946befc 100644 --- a/config/initializers/filter_parameter_logging.rb +++ b/config/initializers/filter_parameter_logging.rb @@ -1,6 +1,9 @@ +# rubocop:disable all # Be sure to restart your server when you modify this file. -# Configure sensitive parameters which will be filtered from the log file. +# Configure parameters to be partially matched (e.g. passw matches password) and filtered from the log file. +# Use this to limit dissemination of sensitive information. +# See the ActiveSupport::ParameterFilter documentation for supported notations and behaviors. Rails.application.config.filter_parameters += [ - :passw, :secret, :_key, :crypt, :salt, :certificate, :otp, :ssn + :passw, :secret, :token, :_key, :crypt, :salt, :certificate, :otp, :ssn ] diff --git a/config/initializers/inflections.rb b/config/initializers/inflections.rb index cf573c56fc..37d3f5ba46 100644 --- a/config/initializers/inflections.rb +++ b/config/initializers/inflections.rb @@ -4,13 +4,17 @@ # are locale specific, and you may define rules for as many different # locales as you wish. All of these examples are active by default: # ActiveSupport::Inflector.inflections(:en) do |inflect| -# inflect.plural /^(ox)$/i, '\1en' -# inflect.singular /^(ox)en/i, '\1' -# inflect.irregular 'person', 'people' +# inflect.plural /^(ox)$/i, "\\1en" +# inflect.singular /^(ox)en/i, "\\1" +# inflect.irregular "person", "people" # inflect.uncountable %w( fish sheep ) # end # These inflection rules are supported but not enabled by default: +# ActiveSupport::Inflector.inflections(:en) do |inflect| +# inflect.acronym "RESTful" +# end + ActiveSupport::Inflector.inflections(:en) do |inflect| inflect.acronym 'HTML' inflect.acronym 'RTF' diff --git a/config/initializers/permissions_policy.rb b/config/initializers/permissions_policy.rb index 00f64d71b0..7db3b9577e 100644 --- a/config/initializers/permissions_policy.rb +++ b/config/initializers/permissions_policy.rb @@ -1,11 +1,13 @@ +# Be sure to restart your server when you modify this file. + # Define an application-wide HTTP permissions policy. For further -# information see https://developers.google.com/web/updates/2018/06/feature-policy -# -# Rails.application.config.permissions_policy do |f| -# f.camera :none -# f.gyroscope :none -# f.microphone :none -# f.usb :none -# f.fullscreen :self -# f.payment :self, "https://secure.example.com" +# information see: https://developers.google.com/web/updates/2018/06/feature-policy + +# Rails.application.config.permissions_policy do |policy| +# policy.camera :none +# policy.gyroscope :none +# policy.microphone :none +# policy.usb :none +# policy.fullscreen :self +# policy.payment :self, "https://secure.example.com" # end diff --git a/config/initializers/secret_token.rb b/config/initializers/secret_token.rb new file mode 100644 index 0000000000..fed239c91a --- /dev/null +++ b/config/initializers/secret_token.rb @@ -0,0 +1,2 @@ +secret_key_base = AlaveteliConfiguration.secret_key_base +Rails.application.credentials.secret_key_base = secret_key_base diff --git a/config/initializers/zeitwerk.rb b/config/initializers/zeitwerk.rb index f07b3fe679..52ae40156c 100644 --- a/config/initializers/zeitwerk.rb +++ b/config/initializers/zeitwerk.rb @@ -9,13 +9,8 @@ ) Rails.autoloaders.main.ignore( - "lib/acts_as_xapian", "lib/confidence_intervals.rb", "lib/configuration.rb", - "lib/core_ext", - "lib/custom_cops", - "lib/generators", - "lib/has_tag_string", "lib/i18n_fixes.rb", "lib/languages.rb", "lib/mail_handler/backends/mail_extensions.rb", @@ -25,6 +20,5 @@ "lib/routing_filters.rb", "lib/stripe_mock_patch.rb", "lib/theme.rb", - "lib/themes", "lib/use_spans_for_errors.rb" ) diff --git a/config/secrets.yml b/config/secrets.yml deleted file mode 100644 index f91266d509..0000000000 --- a/config/secrets.yml +++ /dev/null @@ -1,8 +0,0 @@ -development: - secret_key_base: <%= AlaveteliConfiguration.secret_key_base %> - -test: - secret_key_base: <%= AlaveteliConfiguration.secret_key_base %> - -production: - secret_key_base: <%= AlaveteliConfiguration.secret_key_base %> diff --git a/config/storage.yml-example b/config/storage.yml-example index 8fc506215c..3017b4e282 100644 --- a/config/storage.yml-example +++ b/config/storage.yml-example @@ -14,6 +14,10 @@ # project: '' # bucket: '' +local: + service: Disk + root: <%= Rails.root.join('storage/local') %> + test: service: Disk root: <%= Rails.root.join('tmp/storage') %> diff --git a/db/migrate/20250108184817_add_service_name_to_active_storage_blobs.active_storage.rb b/db/migrate/20250108184817_add_service_name_to_active_storage_blobs.active_storage.rb new file mode 100644 index 0000000000..e46c801bb7 --- /dev/null +++ b/db/migrate/20250108184817_add_service_name_to_active_storage_blobs.active_storage.rb @@ -0,0 +1,23 @@ +# rubocop:disable all +# This migration comes from active_storage (originally 20190112182829) +class AddServiceNameToActiveStorageBlobs < ActiveRecord::Migration[6.0] + def up + return unless table_exists?(:active_storage_blobs) + + unless column_exists?(:active_storage_blobs, :service_name) + add_column :active_storage_blobs, :service_name, :string + + if configured_service = ActiveStorage::Blob.service.name + ActiveStorage::Blob.unscoped.update_all(service_name: configured_service) + end + + change_column :active_storage_blobs, :service_name, :string, null: false + end + end + + def down + return unless table_exists?(:active_storage_blobs) + + remove_column :active_storage_blobs, :service_name + end +end diff --git a/db/migrate/20250108184818_create_active_storage_variant_records.active_storage.rb b/db/migrate/20250108184818_create_active_storage_variant_records.active_storage.rb new file mode 100644 index 0000000000..f33d31f80f --- /dev/null +++ b/db/migrate/20250108184818_create_active_storage_variant_records.active_storage.rb @@ -0,0 +1,28 @@ +# rubocop:disable all +# This migration comes from active_storage (originally 20191206030411) +class CreateActiveStorageVariantRecords < ActiveRecord::Migration[6.0] + def change + return unless table_exists?(:active_storage_blobs) + + # Use Active Record's configured type for primary key + create_table :active_storage_variant_records, id: primary_key_type, if_not_exists: true do |t| + t.belongs_to :blob, null: false, index: false, type: blobs_primary_key_type + t.string :variation_digest, null: false + + t.index %i[ blob_id variation_digest ], name: "index_active_storage_variant_records_uniqueness", unique: true + t.foreign_key :active_storage_blobs, column: :blob_id + end + end + + private + def primary_key_type + config = Rails.configuration.generators + config.options[config.orm][:primary_key_type] || :primary_key + end + + def blobs_primary_key_type + pkey_name = connection.primary_key(:active_storage_blobs) + pkey_column = connection.columns(:active_storage_blobs).find { |c| c.name == pkey_name } + pkey_column.bigint? ? :bigint : pkey_column.type + end +end diff --git a/db/migrate/20250108184819_remove_not_null_on_active_storage_blobs_checksum.active_storage.rb b/db/migrate/20250108184819_remove_not_null_on_active_storage_blobs_checksum.active_storage.rb new file mode 100644 index 0000000000..93c8b85ade --- /dev/null +++ b/db/migrate/20250108184819_remove_not_null_on_active_storage_blobs_checksum.active_storage.rb @@ -0,0 +1,8 @@ +# This migration comes from active_storage (originally 20211119233751) +class RemoveNotNullOnActiveStorageBlobsChecksum < ActiveRecord::Migration[6.0] + def change + return unless table_exists?(:active_storage_blobs) + + change_column_null(:active_storage_blobs, :checksum, true) + end +end diff --git a/doc/CHANGES.md b/doc/CHANGES.md index 8b6b98eb81..6aba2958f6 100644 --- a/doc/CHANGES.md +++ b/doc/CHANGES.md @@ -2,6 +2,7 @@ ## Highlighted Features +* Upgrade to Rails 7.1 (Graeme Porteous) * Update Rails application framework defaults (Graeme Porteous) * Drop support for Ruby 3.1 (Graeme Porteous) diff --git a/gems/alaveteli_features/alaveteli_features.gemspec b/gems/alaveteli_features/alaveteli_features.gemspec index f25034c545..dc25e60d74 100644 --- a/gems/alaveteli_features/alaveteli_features.gemspec +++ b/gems/alaveteli_features/alaveteli_features.gemspec @@ -19,7 +19,7 @@ Gem::Specification.new do |spec| spec.test_files = spec.files.grep(%r{^(test|spec|features)/}) spec.require_paths = ["lib"] - spec.add_dependency "rails", ">= 7.0.4", "< 8.1.0" + spec.add_dependency "rails", ">= 7.1.5.1", "< 7.2.0" spec.add_dependency "flipper", "~> 1.3.2" spec.add_dependency "flipper-active_record", "~> 1.3.2" # Mime types 3 needs Ruby 2.0.0 or greater, but we need to support 1.9.3 so diff --git a/lib/no_constraint_disabling.rb b/lib/no_constraint_disabling.rb index fdebebfa4b..c8132524a3 100644 --- a/lib/no_constraint_disabling.rb +++ b/lib/no_constraint_disabling.rb @@ -26,11 +26,7 @@ module ActiveRecord class FixtureSet def self.create_fixtures(fixtures_directory, fixture_set_names, class_names = {}, config = ActiveRecord::Base) fixture_set_names = Array(fixture_set_names).map(&:to_s) - if Rails.version < '7.1.0' - class_names = ClassCache.new class_names, config - else - class_names.stringify_keys! - end + class_names.stringify_keys! # FIXME: Apparently JK uses this. connection = block_given? ? yield : ActiveRecord::Base.connection diff --git a/script/load-sample-data b/script/load-sample-data index 1fb8a51ee2..3abaa1320b 100755 --- a/script/load-sample-data +++ b/script/load-sample-data @@ -13,7 +13,7 @@ require Rails.root.join("spec", "support", "load_file_fixtures") require Rails.root.join("spec", "support", "email_helpers") RSpec.configure do |config| - config.fixture_path = Rails.root.join("spec","fixtures") + config.fixture_paths = [Rails.root.join("spec", "fixtures")] end # HACK: Normally to load fixtures you'd run `rake db:fixtures:load` (with diff --git a/spec/models/incoming_message_spec.rb b/spec/models/incoming_message_spec.rb index 48c0c8c247..151be5a123 100644 --- a/spec/models/incoming_message_spec.rb +++ b/spec/models/incoming_message_spec.rb @@ -644,7 +644,10 @@ end it "should correctly fold various types of footer" do - Dir.glob(File.join(RSpec.configuration.fixture_path, "files", "email-folding-example-*.txt")).each do |file| + path = Rails.root.join( + "spec", "fixtures", "files", "email-folding-example-*.txt" + ) + Dir.glob(path).each do |file| message = File.read(file) parsed = IncomingMessage.remove_quoted_sections(message) expected = File.read("#{file}.expected") diff --git a/spec/spec_helper.rb b/spec/spec_helper.rb index 6d45cc62a4..dae8b94c0e 100644 --- a/spec/spec_helper.rb +++ b/spec/spec_helper.rb @@ -41,7 +41,7 @@ config.include StripAttributes::Matchers # Remove this line if you're not using ActiveRecord or ActiveRecord fixtures - config.fixture_path = "#{::Rails.root}/spec/fixtures" + config.fixture_paths = [Rails.root.join("spec", "fixtures")] # The order (!) of this is important thanks to foreign keys config.global_fixtures = :users, diff --git a/spec/support/email_helpers.rb b/spec/support/email_helpers.rb index 9f7eab508c..f0c89a613b 100644 --- a/spec/support/email_helpers.rb +++ b/spec/support/email_helpers.rb @@ -1,5 +1,5 @@ def load_raw_emails_data - raw_emails_yml = File.join(RSpec.configuration.fixture_path, "raw_emails.yml") + raw_emails_yml = Rails.root.join("spec", "fixtures", "raw_emails.yml") YAML.load_file(raw_emails_yml).map { |_k,v| v["id"] }.each do |raw_email_id| raw_email = RawEmail.find(raw_email_id) raw_email.data = load_file_fixture(format("raw_emails/%d.email", raw_email_id)) diff --git a/spec/support/load_file_fixtures.rb b/spec/support/load_file_fixtures.rb index af5b672a27..d60da19efe 100644 --- a/spec/support/load_file_fixtures.rb +++ b/spec/support/load_file_fixtures.rb @@ -1,5 +1,5 @@ def file_fixture_name(file_name) - File.join(RSpec.configuration.fixture_path, "files", file_name) + Rails.root.join("spec", "fixtures", "files", file_name).to_s end def load_file_fixture(file_name, mode = 'rb') @@ -9,10 +9,10 @@ def load_file_fixture(file_name, mode = 'rb') def read_described_class_fixture(fixture) base_path = described_class.name.underscore - File.read(File.join(RSpec.configuration.fixture_path, base_path, fixture)) + File.read(Rails.root.join("spec", "fixtures", base_path, fixture)) end def read_described_template_fixture described_template = self.class.top_level_description.gsub(/\..*\.erb/, '') - File.read(File.join(RSpec.configuration.fixture_path, described_template)) + File.read(Rails.root.join("spec", "fixtures", described_template)) end