fix: repair DashboardState.__init__ (my prior commit orphaned _backtest_lock)

The self-heal commit (a00f967) inserted the _research method INSIDE __init__ at
method-body indent, truncating it so _change_signal/_backtest_lock/_backtest_
cache never got set -> AttributeError on backtest. Moved _research to a sibling
method; __init__ now sets all attrs. Two chart/sparkline tests updated: a None
research_con now REOPENS lazily, so 'no research db attached' is reached only
when the reopen also fails (they monkeypatch open to fail). 22 api tests green.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
momentum devandClaude Fable 5 committed 2026-07-20 12:06:19 -05:00
1 parent a00f967bdf
commit e7bd8fa279
3 files changed
+17 -9

No files matched your search

+7 -7
View File
@@ -257,6 +257,13 @@ class DashboardState:
self.watch_inject = watch_inject
self._lock = threading.Lock()
self._research_lock = threading.Lock()
# lazily-built, process-wide SSE change signal (shared by all clients)
self._change_signal: _ChangeSignal | None = None
# backtest replay cache (plan 015) — a DEDICATED lock, not self._lock,
# so a slow replay (10-30s) never blocks the live snapshot/SSE path.
# key = (since, until, repr(settings)) -> (result, monotonic timestamp).
self._backtest_lock = threading.Lock()
self._backtest_cache: dict = {}
def _research(self):
"""The research DB connection, opened LAZILY and self-healing. It used
@@ -276,13 +283,6 @@ class DashboardState:
logger.warning("research DB open failed (charts empty): %s", exc)
self.research_con = None
return self.research_con
# lazily-built, process-wide SSE change signal (shared by all clients)
self._change_signal: _ChangeSignal | None = None
# backtest replay cache (plan 015) — a DEDICATED lock, not self._lock,
# so a slow replay (10-30s) never blocks the live snapshot/SSE path.
# key = (since, until, repr(settings)) -> (result, monotonic timestamp).
self._backtest_lock = threading.Lock()
self._backtest_cache: dict = {}
def change_stamp(self):
"""SSE change token from the shared once-per-second signal (see _ChangeSignal)."""