This commit is contained in:
Mateusz Gruszczyński
2026-08-17 10:07:19 +02:00
parent 074d17be89
commit cc3c446c8e
29 changed files with 627 additions and 105 deletions
+68
View File
@@ -175,6 +175,74 @@ class PrometheusMetricsTests(unittest.TestCase):
store.close()
def test_health_endpoint_uses_lightweight_provider(self):
with tempfile.TemporaryDirectory() as tmp:
db_path = str(Path(tmp) / "ids.db")
cfg = replace(Config.from_env(), web_bind="127.0.0.1", web_port=0, db_path=db_path)
store = AlertStore(db_path)
full_calls = []
health_calls = []
def full_status():
full_calls.append(True)
raise AssertionError("lightweight health endpoint must not build full status")
web = WebServer(
cfg,
store,
full_status,
healthcheck_provider=lambda: health_calls.append(True) or {"status": "ok", "operational": True},
)
try:
with contextlib.redirect_stdout(io.StringIO()):
web.start()
port = web.server.server_address[1]
with urllib.request.urlopen(f"http://127.0.0.1:{port}/api/health", timeout=2) as response:
body = response.read().decode("utf-8")
self.assertEqual(200, response.status)
self.assertIn('"operational":true', body.replace(" ", ""))
self.assertEqual([], full_calls)
self.assertEqual([True], health_calls)
finally:
web.stop()
store.close()
def test_status_payload_is_cached_for_short_poll_bursts(self):
with tempfile.TemporaryDirectory() as tmp:
db_path = str(Path(tmp) / "ids.db")
cfg = replace(Config.from_env(), web_bind="127.0.0.1", web_port=0, db_path=db_path)
store = AlertStore(db_path)
calls = []
web = WebServer(cfg, store, lambda: calls.append(True) or {"operational": True})
try:
first = web._status_payload()
second = web._status_payload()
self.assertTrue(first["operational"])
self.assertTrue(second["operational"])
self.assertEqual([True], calls)
finally:
web.server.server_close()
store.close()
def test_stats_payload_caches_expensive_sqlite_aggregates(self):
with tempfile.TemporaryDirectory() as tmp:
db_path = str(Path(tmp) / "ids.db")
cfg = replace(Config.from_env(), web_bind="127.0.0.1", web_port=0, db_path=db_path)
store = AlertStore(db_path)
calls = {"summary": 0, "analytics": 0, "ndr": 0}
store.summary = lambda: calls.__setitem__("summary", calls["summary"] + 1) or {"alerts": 0}
store.analytics = lambda: calls.__setitem__("analytics", calls["analytics"] + 1) or {"alerts_24h": 0}
store.ndr_summary = lambda: calls.__setitem__("ndr", calls["ndr"] + 1) or {"open_incidents": 0}
web = WebServer(cfg, store, lambda: {"operational": True})
try:
first = web._stats_payload()
second = web._stats_payload()
self.assertEqual(first, second)
self.assertEqual({"summary": 1, "analytics": 1, "ndr": 1}, calls)
finally:
web.server.server_close()
store.close()
def test_metrics_ip_acl_denies_before_rendering_metrics(self):
with tempfile.TemporaryDirectory() as tmp:
db_path = str(Path(tmp) / "ids.db")