amazon-transcreation/backend/app/ws/manager.py
DJP 98fa16bfc3 feat: complete Phase 1-2 scaffold — backend, frontend, pipeline skeleton
Full-stack Amazon AI Transcreation Platform with:
- FastAPI backend (async, PostgreSQL, Redis, Celery) with 11 DB tables
- JWT auth (SSO-ready abstract provider pattern)
- 6-agent pipeline orchestrator with deterministic modules
- Next.js 14 frontend with Amazon branding (Ember fonts, orange/dark theme)
- Job wizard, monitoring HUD, output review, admin screens
- 154 TM/reference files imported, 12 locales configured
- Docker Compose for all services

Agents 2-5 (TM retrieval, ranker, transcreator, compliance) are stubs
pending Phase 3 LLM integration.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-04-10 12:31:43 -04:00

59 lines
2 KiB
Python

import json
from typing import Any
from fastapi import WebSocket
class ConnectionManager:
"""Manage WebSocket connections grouped by job_id."""
def __init__(self) -> None:
self._connections: dict[str, list[WebSocket]] = {}
async def connect(self, job_id: str, websocket: WebSocket) -> None:
"""Accept a websocket connection and register it for a job."""
await websocket.accept()
if job_id not in self._connections:
self._connections[job_id] = []
self._connections[job_id].append(websocket)
def disconnect(self, job_id: str, websocket: WebSocket) -> None:
"""Remove a websocket connection from a job's connection list."""
if job_id in self._connections:
self._connections[job_id] = [
ws for ws in self._connections[job_id] if ws != websocket
]
if not self._connections[job_id]:
del self._connections[job_id]
async def broadcast(self, job_id: str, message: dict[str, Any]) -> None:
"""Broadcast a JSON message to all connections for a job."""
if job_id not in self._connections:
return
payload = json.dumps(message)
disconnected: list[WebSocket] = []
for websocket in self._connections[job_id]:
try:
await websocket.send_text(payload)
except Exception:
disconnected.append(websocket)
# Clean up dead connections
for ws in disconnected:
self.disconnect(job_id, ws)
async def send_personal(
self, websocket: WebSocket, message: dict[str, Any]
) -> None:
"""Send a message to a specific websocket."""
await websocket.send_text(json.dumps(message))
def get_connection_count(self, job_id: str) -> int:
"""Get the number of active connections for a job."""
return len(self._connections.get(job_id, []))
# Singleton instance
manager = ConnectionManager()