fester/backend/api/ws.py

49 lines
1.5 KiB
Python
Executable File

"""
WebSocketStream — legacy bridge between the EventBus and WebSocket clients.
NOTE: The real broadcasting is now done in backend/main.py via
`_ws_broadcast` which properly awaits the async send. This class is kept
for backward compatibility with the api.py facade, but its `attach_bus`
method is a no-op (the actual wiring happens in main.py).
F-15 remediation: the shared ``clients`` list is now guarded by a lock
so concurrent register/unregister calls from multiple WS handlers
can't race.
"""
from __future__ import annotations
import threading
from typing import Any, List
from backend.events.bus import EventBus
class WebSocketStream:
def __init__(self) -> None:
self._lock = threading.Lock()
self.clients: List[Any] = [] # shared with main.py's hub.clients
def attach_bus(self, bus: EventBus) -> None:
"""No-op — broadcasting is wired in backend/main.py via _ws_broadcast.
Kept for backward compat with api.py's attach_ws_stream().
"""
pass
def register_client(self, client: Any) -> None:
with self._lock:
self.clients.append(client)
def unregister_client(self, client: Any) -> None:
with self._lock:
try:
self.clients.remove(client)
except ValueError:
pass
def snapshot_clients(self) -> List[Any]:
"""Return a snapshot copy of the client list (safe for iteration)."""
with self._lock:
return list(self.clients)