"""Prometheus queries — node load lookups. F-06 remediation: ``PROM_URL`` is now resolved from ``backend.config.EXTERNAL_CONFIG["prometheus_url"]`` (env-var ``FESTER_PROM_URL``) instead of being hardcoded. """ from __future__ import annotations import logging from typing import Optional import requests from backend.config import EXTERNAL_CONFIG log = logging.getLogger(__name__) def _prom_url() -> str: """Return the current Prometheus URL. Read at call time so tests / operators can monkey-patch the env var between requests without restarting the process. """ import os return os.environ.get( "FESTER_PROM_URL", EXTERNAL_CONFIG.get("prometheus_url", "http://localhost:9090"), ) def get_node_load(node: str) -> float: """Return the 1-minute load average for ``node``. Falls back to 1.0 on any error (Prometheus down, metric missing, network error) so the scheduler always gets a usable number. """ query = f'node_load1{{instance="{node}"}}' try: r = requests.get( f"{_prom_url()}/api/v1/query", params={"query": query}, timeout=5, ) r.raise_for_status() data = r.json() result = data.get("data", {}).get("result", []) if not result: log.debug("prometheus returned no data for %s", node) return 1.0 return float(result[0]["value"][1]) except Exception as e: log.debug("prometheus lookup failed for %s: %s", node, e) return 1.0