@startuml title Notification System - Polling Architecture Sequence actor User participant "React Frontend" as Frontend participant "Flask API" as API database "PostgreSQL" as DB participant "Background Job\n(event source)" as EventSource == Event Generation == EventSource -> EventSource: Detect event\n(new message, status change, etc) EventSource -> EventSource: Check user preferences\n(is this event type enabled?) EventSource -> DB: INSERT INTO notifications\n(user_id, event_type, message, read=false) note right: Sanitize message here\n(single choke point for XSS) DB --> EventSource: OK == Polling Loop (every 30s) == loop Every 30 seconds Frontend -> API: GET /api/notifications/unread note right: Headers: session cookie\n(existing auth) API -> API: Extract user_id from session API -> DB: SELECT * FROM notifications\nWHERE user_id = ? AND read = false\nORDER BY created_at DESC DB --> API: [notification rows] API -> API: Rate limit check\n(Flask-Limiter: 100/min) API --> Frontend: JSON array of notifications alt New notifications exist Frontend -> Frontend: Filter by user preferences\n(double-check client-side) Frontend -> User: Show browser notification\n(Browser Notification API) User -> Frontend: Click notification Frontend -> API: PATCH /api/notifications/{id}/read API -> DB: UPDATE notifications\nSET read = true WHERE id = ? DB --> API: OK API --> Frontend: 200 OK end end == User Preferences Management == User -> Frontend: Toggle preference\n("disable status change notifications") Frontend -> API: PUT /api/preferences API -> DB: UPDATE user_preferences\nSET event_type_enabled = false DB --> API: OK API --> Frontend: 200 OK note over Frontend, DB **Key Architectural Properties:** - Stateless: No connection state to manage - Simple: Standard HTTP request/response - Scalable: ~33 req/s for 1000 users - Secure: Session auth + rate limiting + sanitization - Evolvable: Can swap to SSE/WS without changing much end note @enduml