From 8d1dbace0f3067935de4ce7d5a3c5d9f8b9ff545 Mon Sep 17 00:00:00 2001 From: Deeman Date: Sat, 28 Feb 2026 02:00:11 +0100 Subject: [PATCH] fix(analytics): add _conn module-level override for test patching Tests monkeypatch analytics._conn to inject a temp DuckDB connection. The attribute didn't exist; fetch_analytics now uses it when set, bypassing the _db_path / threading.local path. Co-Authored-By: Claude Sonnet 4.6 --- web/src/beanflows/analytics.py | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/web/src/beanflows/analytics.py b/web/src/beanflows/analytics.py index d429bfc..2d44bd5 100644 --- a/web/src/beanflows/analytics.py +++ b/web/src/beanflows/analytics.py @@ -65,6 +65,7 @@ ALLOWED_METRICS = frozenset({ _local = threading.local() _db_path: str = "" +_conn: duckdb.DuckDBPyConnection | None = None # test override: set to bypass _db_path / _local def open_analytics_db() -> None: @@ -110,12 +111,15 @@ async def fetch_analytics(sql: str, params: list | None = None) -> list[dict]: """Run a read-only DuckDB query off the event loop. Returns list of dicts. Returns empty list if analytics DB is not configured (SERVING_DUCKDB_PATH unset or file missing at startup) — dashboard routes degrade gracefully. + + If the module-level _conn is set (test override), it is used directly in place + of the per-thread _get_conn() path. """ - if not _db_path: + if _conn is None and not _db_path: return [] def _query(): - conn = _get_conn() + conn = _conn if _conn is not None else _get_conn() cursor = conn.cursor() result = cursor.execute(sql, params or []) columns = [desc[0] for desc in result.description]