fix: split HTTP connect/read timeouts (Jellyfin build + qBit stats)
Every HTTP client passed an integer timeout to requests, applying the same value to BOTH connect and read phases. A slow Jellyfin /Items page or qBit /sync/maindata blew through the 10s read budget → ReadTimeoutError. Split into a (connect=5s, read=60s default) tuple via shared http_timeout() helper. The media index build worker uses a 180s read floor. Existing services with low timeout_seconds benefit from bumping to 60+.
This commit is contained in:
@@ -25,7 +25,7 @@ class AlertmanagerConfig(ServiceConfigBase):
|
||||
"""Non-secret Alertmanager connection config."""
|
||||
|
||||
base_url: ServiceBaseUrl
|
||||
timeout_seconds: int = 5
|
||||
timeout_seconds: int = 15
|
||||
|
||||
|
||||
class AlertmanagerAlertsWidgetConfig(WidgetConfigBase):
|
||||
@@ -83,7 +83,7 @@ def test_connection(
|
||||
"""GET /api/v2/status with optional bearer auth."""
|
||||
try:
|
||||
base_url = str(config.get("base_url") or "").rstrip("/")
|
||||
timeout = int(config.get("timeout_seconds") or 5)
|
||||
timeout = int(config.get("timeout_seconds") or 15)
|
||||
headers: dict[str, str] = {}
|
||||
api_key = str(secrets.get("api_key") or "")
|
||||
if api_key:
|
||||
|
||||
@@ -33,7 +33,7 @@ def test_connection(
|
||||
try:
|
||||
base_url = str(config.get("base_url") or "").rstrip("/")
|
||||
api_token = str(secrets.get("api_token") or "")
|
||||
timeout = float(config.get("timeout_seconds") or 10)
|
||||
timeout = float(config.get("timeout_seconds") or 60)
|
||||
client = AuthentikClient(base_url=base_url, api_token=api_token, timeout=timeout)
|
||||
result = client.users(page=1, page_size=1)
|
||||
total = result.get("total", 0) if isinstance(result, dict) else 0
|
||||
@@ -46,7 +46,7 @@ class AuthentikConfig(ServiceConfigBase):
|
||||
"""Non-secret Authentik connection config."""
|
||||
|
||||
base_url: ServiceBaseUrl
|
||||
timeout_seconds: int = 10
|
||||
timeout_seconds: int = 60
|
||||
|
||||
|
||||
DEFINITION = ServiceDefinition(
|
||||
|
||||
@@ -29,7 +29,7 @@ def test_connection(
|
||||
try:
|
||||
base_url = str(config.get("base_url") or "")
|
||||
api_key = str(secrets.get("api_key") or "")
|
||||
timeout = int(config.get("timeout_seconds") or 10)
|
||||
timeout = int(config.get("timeout_seconds") or 60)
|
||||
client = JellyfinClient(base_url, api_key, timeout=timeout)
|
||||
users = client.users()
|
||||
return TestResult(ok=True, detail="Connected to Jellyfin.", evidence=f"{len(users)} users")
|
||||
@@ -49,7 +49,7 @@ class JellyfinConfig(ServiceConfigBase):
|
||||
|
||||
base_url: ServiceBaseUrl
|
||||
user_id: str = ""
|
||||
timeout_seconds: int = 10
|
||||
timeout_seconds: int = 60
|
||||
jellyseerr_url: str = ""
|
||||
jellyseerr_api_key: str = ""
|
||||
|
||||
|
||||
@@ -31,7 +31,7 @@ def test_connection(
|
||||
"""GET {base_url}/status.php (unauthenticated server probe)."""
|
||||
try:
|
||||
base_url = str(config.get("base_url") or "").rstrip("/")
|
||||
resp = requests.get(f"{base_url}/status.php", timeout=10)
|
||||
resp = requests.get(f"{base_url}/status.php", timeout=(5.0, 60.0))
|
||||
resp.raise_for_status()
|
||||
payload = resp.json()
|
||||
version = str(payload.get("version", "") or "connected")
|
||||
|
||||
@@ -31,7 +31,7 @@ def test_connection(
|
||||
grafana_url = str(config.get("grafana_url") or "").rstrip("/")
|
||||
api_key = str(secrets.get("grafana_api_key") or "")
|
||||
datasource_uid = str(config.get("datasource_uid") or "prometheus")
|
||||
timeout = int(config.get("timeout_seconds") or 10)
|
||||
timeout = int(config.get("timeout_seconds") or 60)
|
||||
if not grafana_url:
|
||||
return TestResult(ok=False, detail="Grafana gateway URL is required.")
|
||||
if not api_key:
|
||||
@@ -73,7 +73,7 @@ class PrometheusConfig(ServiceConfigBase):
|
||||
|
||||
grafana_url: ServiceBaseUrl
|
||||
datasource_uid: str = "prometheus"
|
||||
timeout_seconds: int = 10
|
||||
timeout_seconds: int = 60
|
||||
|
||||
|
||||
class PrometheusMetricWidgetConfig(WidgetConfigBase):
|
||||
|
||||
@@ -35,7 +35,7 @@ def test_connection(
|
||||
base_url = str(config.get("base_url") or "")
|
||||
username = str(secrets.get("username") or "")
|
||||
password = str(secrets.get("password") or "")
|
||||
timeout = int(config.get("timeout_seconds") or 10)
|
||||
timeout = int(config.get("timeout_seconds") or 60)
|
||||
client = QbittorrentClient(base_url, username, password, timeout=timeout)
|
||||
data = client.maindata()
|
||||
version = str(data.get("server_state", {}).get("qbittorrent_version", "") or "connected")
|
||||
@@ -53,7 +53,7 @@ class QbittorrentConfig(ServiceConfigBase):
|
||||
"""Non-secret qBittorrent connection config."""
|
||||
|
||||
base_url: ServiceBaseUrl
|
||||
timeout_seconds: int = 10
|
||||
timeout_seconds: int = 60
|
||||
|
||||
|
||||
class QbittorrentWidgetConfig(WidgetConfigBase):
|
||||
|
||||
Reference in New Issue
Block a user