aboutsummaryrefslogtreecommitdiffstats
path: root/packages/meshbay-hub/src/meshbay_hub/config.py
diff options
context:
space:
mode:
authorChristophe Besson <cbesson@gmail.com>2026-09-15 02:16:39 +0200
committerChristophe Besson <cbesson@gmail.com>2026-09-15 02:21:01 +0200
commit73ad8e4eb566fe682107fa7e50ef624591199e99 (patch)
treeff0017d014d46d8835487c080dca55c6def7fd6b /packages/meshbay-hub/src/meshbay_hub/config.py
parentbdefcd025604f2c3009fe5e0cc01213c2ba62a6a (diff)
downloadmeshbay-73ad8e4eb566fe682107fa7e50ef624591199e99.tar.gz
feat(hub): session lifetime is an admin setting, and a browser signs out when idle
Browser idle sign-out (media playback counts as activity; not the desktop app), refresh idle window and maximum session length, in hours. Sign-out now revokes on the hub, and the profile has "sign out everywhere". Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01XuNrwLf5EFWCMHzfoEvnpm
Diffstat (limited to 'packages/meshbay-hub/src/meshbay_hub/config.py')
-rw-r--r--packages/meshbay-hub/src/meshbay_hub/config.py15
1 files changed, 11 insertions, 4 deletions
diff --git a/packages/meshbay-hub/src/meshbay_hub/config.py b/packages/meshbay-hub/src/meshbay_hub/config.py
index 827538c..876583e 100644
--- a/packages/meshbay-hub/src/meshbay_hub/config.py
+++ b/packages/meshbay-hub/src/meshbay_hub/config.py
@@ -9,6 +9,7 @@ Priority (highest first):
Production config file example: /etc/meshbay/hub.toml
"""
+import logging
import os
from dataclasses import dataclass, field
from pathlib import Path
@@ -18,6 +19,8 @@ try:
except ImportError:
import tomli as tomllib # type: ignore[no-redef]
+log = logging.getLogger(__name__)
+
DEFAULT_CONFIG_PATHS = [
Path("/etc/meshbay/hub.toml"),
Path.home() / ".config" / "meshbay" / "hub.toml",
@@ -47,8 +50,9 @@ class HubIdentityConfig:
@dataclass
class JWTConfig:
# How long an access token stays good. It is not the session — the refresh
- # token below is, and the SPA renews against it well before this runs out,
- # so a film or a working day never meets this number.
+ # token is, and the SPA renews against it well before this runs out, so a
+ # film or a working day never meets this number. How long the session
+ # lasts is an admin setting (`hub_settings.SESSION_*`), not configuration.
#
# What it does bound is a token that leaks: revoking a member or suspending
# an account both take effect at once (the hub reloads the account on every
@@ -58,7 +62,6 @@ class JWTConfig:
# exercised constantly rather than twice, and cannot rot unnoticed the way
# it did when nothing used it at all.
access_token_ttl: int = 14400 # 4 hours
- refresh_token_ttl: int = 86400 * 30 # 30 days
@dataclass
@@ -161,7 +164,11 @@ def load_config(path: Path | None = None) -> HubConfig:
cfg.identity.admin_usernames = list(admins)
if jwt := raw.get("jwt", {}):
cfg.jwt.access_token_ttl = jwt.get("access_token_ttl", cfg.jwt.access_token_ttl)
- cfg.jwt.refresh_token_ttl = jwt.get("refresh_token_ttl", cfg.jwt.refresh_token_ttl)
+ # One source for the session's length: a value left here would
+ # otherwise look authoritative and change nothing.
+ if "refresh_token_ttl" in jwt:
+ log.warning("%s: [jwt] refresh_token_ttl is ignored — session "
+ "lifetime is set in the admin panel", p)
if ml := raw.get("mail", {}):
for name in (
"destination_cooldown_seconds", "destination_daily_cap",