diff --git a/app/helpers/warning_bar_helper.rb b/app/helpers/warning_bar_helper.rb index 14063b5752f..388d8626d0f 100644 --- a/app/helpers/warning_bar_helper.rb +++ b/app/helpers/warning_bar_helper.rb @@ -40,7 +40,7 @@ module WarningBarHelper end def setting_protocol_mismatched? - request.ssl? != OpenProject::Configuration.secure_connection? + request.ssl? != OpenProject::Configuration.https? end def setting_hostname_mismatched? diff --git a/app/models/setting/aliases.rb b/app/models/setting/aliases.rb index 6bf0524acab..4d6a812ae9b 100644 --- a/app/models/setting/aliases.rb +++ b/app/models/setting/aliases.rb @@ -33,7 +33,7 @@ class Setting ## # Restore the previous Setting.protocol now replaced by https? def protocol - if OpenProject::Configuration.secure_connection? + if OpenProject::Configuration.https? 'https' else 'http' diff --git a/config/constants/settings/definitions.rb b/config/constants/settings/definitions.rb index 61c1c4649ce..fab20d6e42d 100644 --- a/config/constants/settings/definitions.rb +++ b/config/constants/settings/definitions.rb @@ -666,16 +666,16 @@ Settings::Definition.define do writable: false # Assume we're running in an TLS terminated connection. - # This does not affect HSTS, use +rails_force_ssl+ for that. add :https, format: :boolean, default: Rails.env.production?, writable: false - # Enable HTTPS and HSTS - add :rails_force_ssl, + # Allow disabling of HSTS headers and http -> https redirects + # for non-localhost hosts + add :hsts, format: :boolean, - default: Rails.env.production?, + default: -> { https? }, writable: false add :registration_footer, diff --git a/config/environments/production.rb b/config/environments/production.rb index 4e1bc072af0..e8313eeea64 100644 --- a/config/environments/production.rb +++ b/config/environments/production.rb @@ -74,19 +74,30 @@ OpenProject::Application.configure do # Store uploaded files on the local file system (see config/storage.yml for options) # config.active_storage.service = :local - # Force all access to the app over SSL, use Strict-Transport-Security, and use secure cookies. - config.force_ssl = ActiveModel::Type::Boolean.new.cast(OpenProject::Configuration['rails_force_ssl']) + # When https is configured, Force all access to the app over SSL, use Strict-Transport-Security, and use secure cookies. + # Allow disabling HSTS redirect by using OPENPROJECT_HSTS=false + config.force_ssl = OpenProject::Configuration.https? config.ssl_options = { # Disable redirect on the internal SYS API redirect: { + hsts: OpenProject::Configuration.hsts?, exclude: ->(request) do + # Disable redirects when hsts is disabled + return true unless OpenProject::Configuration.hsts? + # Respect the relative URL relative_url = Regexp.escape(OpenProject::Configuration['rails_relative_url_root']) + # When we match SYS controller API, allow non-https access - request.path =~ /#{relative_url}\/sys\// || request.path =~ /#{relative_url}\/health_checks/ + return true if request.path =~ /#{relative_url}\/sys\// + + # When we match health checks + return true if request.path =~ /#{relative_url}\/health_checks/ + + false end }, - secure_cookies: true + secure_cookies: OpenProject::Configuration.https? } # Set to :debug to see everything in the log. diff --git a/config/initializers/session_store.rb b/config/initializers/session_store.rb index 8412c38f44c..326d87f9126 100644 --- a/config/initializers/session_store.rb +++ b/config/initializers/session_store.rb @@ -79,7 +79,7 @@ relative_url_root = config['rails_relative_url_root'].presence session_options = { key: config['session_cookie_name'], httponly: true, - secure: config.secure_connection?, + secure: config.https?, path: relative_url_root } diff --git a/lib_static/open_project/configuration/helpers.rb b/lib_static/open_project/configuration/helpers.rb index 1cb6abf59d0..7a061f7f1ec 100644 --- a/lib_static/open_project/configuration/helpers.rb +++ b/lib_static/open_project/configuration/helpers.rb @@ -32,12 +32,6 @@ module OpenProject # To be included into OpenProject::Configuration in order to provide # helper methods for easier access to certain configuration options. module Helpers - ## - # Are we behind a TLS terminated session? - def secure_connection? - https? || rails_force_ssl? - end - def direct_uploads return false unless direct_uploads_supported? diff --git a/modules/avatars/app/helpers/avatar_helper.rb b/modules/avatars/app/helpers/avatar_helper.rb index 61c097b6017..95e40665f9c 100644 --- a/modules/avatars/app/helpers/avatar_helper.rb +++ b/modules/avatars/app/helpers/avatar_helper.rb @@ -121,7 +121,7 @@ module AvatarHelper def default_gravatar_options { - secure: OpenProject::Configuration.secure_connection?, + secure: OpenProject::Configuration.https?, default: OpenProject::Configuration.gravatar_fallback_image } end diff --git a/modules/two_factor_authentication/app/controllers/concerns/two_factor_authentication/remember_token.rb b/modules/two_factor_authentication/app/controllers/concerns/two_factor_authentication/remember_token.rb index e0ce8bf8756..212c48218b0 100644 --- a/modules/two_factor_authentication/app/controllers/concerns/two_factor_authentication/remember_token.rb +++ b/modules/two_factor_authentication/app/controllers/concerns/two_factor_authentication/remember_token.rb @@ -29,7 +29,7 @@ module ::TwoFactorAuthentication value: new_token!(@authenticated_user), httponly: true, expires: remember_2fa_days.days.from_now, - secure: OpenProject::Configuration.secure_connection? + secure: OpenProject::Configuration.https? } end