Skip to content

Bring the security and hosting docs in line with the current defaults - #2842

Open
joyshmitz wants to merge 3 commits into
FlexMeasures:mainfrom
joyshmitz:docs/security-defaults
Open

joyshmitz wants to merge 3 commits into
FlexMeasures:mainfrom
joyshmitz:docs/security-defaults

Conversation

@joyshmitz

@joyshmitz joyshmitz commented Nov 7, 2026 •

Copy link
Copy Markdown
Contributor

Description

Some security and hosting pages still describe defaults that changed: #1008 (v0.20.0) made the HTTPS redirect opt-in through FLEXMEASURES_FORCE_HTTPS, and #1564 (v0.27.0) turned two-factor authentication off by default. A host reading these pages could assume both are on.

Page Said Actually
concepts/security_auth.rst all data is sent with HTTPS, even via http:// FlexMeasures redirects to https:// only with FLEXMEASURES_FORCE_HTTPS = True (app.py:149, default False in config_defaults.py:226); setting up TLS is up to the host (the Docker image runs gunicorn on plain 0.0.0.0:5000)
concepts/security_auth.rst the UI uses 2FA SECURITY_TWO_FACTOR is False by default (config_defaults.py:81)
concepts/security_auth.rst passwords are hashed with bcrypt Flask-Security's default, Argon2, which FlexMeasures does not override (see the comment at config_defaults.py:309)
concepts/security_auth.rst tokens are encrypted with sha256_crypt and store seconds since 2011; SECURITY_TOKEN_MAX_AGE is an environment variable Flask-Security signs them with itsdangerous's URLSafeTimedSerializer, which stores Unix timestamps; SECURITY_TOKEN_MAX_AGE is not read from the environment (config_utils.py:251-262)
host/docker.rst production mode requires https; SECURITY_TOTP_SECRETS is one of three minimal variables production mode on its own does not enforce HTTPS: with the default settings, a production-mode app answered GET /login over plain http with 200 and no redirect (checked with the Flask test client); TOTP secrets are only loaded when 2FA is on (app.py:141-142)
host/docker.rst, host/installation.rst --env SECURITY_TOTP_SECRETS={"1": "blabla"} in the default commands unquoted, the shell splits this into two arguments, so blabla} lands where Docker expects the image
host/docker.rst the Mapbox token as an example of a setting environment variables cannot set it can be (config_utils.py:256); FLEXMEASURES_FORCE_HTTPS cannot, so that is the example now
host/installation.rst, api/introduction.rst https://localhost:5000/... for a local setup http://, as a local setup has no TLS
  • Rewrite these passages to match the code; in configuration.rst, add a label to FLEXMEASURES_FORCE_HTTPS and say when it redirects (not in debug mode, not with X-Forwarded-Proto: https), that Flask-SSLify's own settings such as SSLIFY_SKIPS apply, and that it is read from the config file only.
  • Added changelog item in documentation/changelog.rst

Look & Feel

Documentation only.

How to test

sphinx-build -M html documentation <out> -W --keep-going -n: locally, the build reports the same 791 warnings as on main (all of them unresolved Python cross-references, such as py:class), and none from the changed pages.

Further Improvements

None.

Related Items

None.


Sign-off

  • I agree to contribute to the project under Apache 2 License.
  • To the best of my knowledge, the proposed patch is not based on code under GPL or other license that is incompatible with FlexMeasures

…efaults

Context:
- FlexMeasures#1008 (first released in v0.20.0) made the HTTPS redirect opt-in through FLEXMEASURES_FORCE_HTTPS, and FlexMeasures#1564 (v0.27.0) turned two-factor authentication off by default, but the docs still described both as always on.
- The pages also described bcrypt password hashes, sha256_crypt tokens with a 2011 epoch, and SECURITY_TOKEN_MAX_AGE as an environment variable, while Flask-Security hashes with Argon2, itsdangerous signs the tokens with Unix timestamps, and that setting is only read from the config file.
- The Docker examples passed SECURITY_TOTP_SECRETS as unquoted JSON with a space, which the shell splits into two arguments, and it is not needed while 2FA is off.

Change:
- security_auth: HTTPS is set up by the host, FLEXMEASURES_FORCE_HTTPS adds the redirect, 2FA is supported and off by default, and the password and token details match the code.
- configuration: a label for FLEXMEASURES_FORCE_HTTPS, when it redirects, the Flask-SSLify settings that apply, and that it is read from the config file only.
- docker, installation: production mode needs no TLS; development mode is for your own computer; drop SECURITY_TOTP_SECRETS from the default commands; an example of a setting environment variables cannot set that is one; http:// for localhost links.
- api/introduction: http://localhost:5000/api for a local server.

Signed-off-by: Serhii <jshmitz@me.com>
Context:
- Hosts read these pages to secure an installation, so the correction belongs in the changelog.

Change:
- Add it under Infrastructure / Support in v1.2.0, with a placeholder for the PR number.

Signed-off-by: Serhii <jshmitz@me.com>
Context:
- The changelog entry was written before the pull request existed.

Change:
- Link it to PR FlexMeasures#2842.

Signed-off-by: Serhii <jshmitz@me.com>
@read-the-docs-community

Copy link
Copy Markdown

Documentation build overview

📚 flexmeasures | 🛠️ Build #35723767 | 📁 Comparing d522695 against latest (48948a1)

  🔍 Preview build  

7 files changed · ± 7 modified

± Modified

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant