diff options
Diffstat (limited to 'web/websocket/notifier.go')
| -rw-r--r-- | web/websocket/notifier.go | 80 |
1 files changed, 41 insertions, 39 deletions
diff --git a/web/websocket/notifier.go b/web/websocket/notifier.go index 2db78578..8115ae0f 100644 --- a/web/websocket/notifier.go +++ b/web/websocket/notifier.go @@ -6,7 +6,7 @@ import ( "github.com/mhsanaei/3x-ui/v2/web/global" ) -// GetHub returns the global WebSocket hub instance +// GetHub returns the global WebSocket hub instance. func GetHub() *Hub { webServer := global.GetWebServer() if webServer == nil { @@ -24,80 +24,82 @@ func GetHub() *Hub { return wsHub } -// HasClients returns true if there are any WebSocket clients connected. +// HasClients returns true if any WebSocket client is connected. // Use this to skip expensive work (DB queries, serialization) when no browser is open. func HasClients() bool { hub := GetHub() - if hub == nil { - return false - } - return hub.GetClientCount() > 0 + return hub != nil && hub.GetClientCount() > 0 } -// BroadcastStatus broadcasts server status update to all connected clients +// BroadcastStatus broadcasts server status update to all connected clients. func BroadcastStatus(status any) { - hub := GetHub() - if hub != nil { + if hub := GetHub(); hub != nil { hub.Broadcast(MessageTypeStatus, status) } } -// BroadcastTraffic broadcasts traffic statistics update to all connected clients +// BroadcastTraffic broadcasts traffic statistics update to all connected clients. func BroadcastTraffic(traffic any) { - hub := GetHub() - if hub != nil { + if hub := GetHub(); hub != nil { hub.Broadcast(MessageTypeTraffic, traffic) } } -// BroadcastInbounds broadcasts inbounds list update to all connected clients +// BroadcastClientStats broadcasts absolute per-client traffic counters for the +// clients that had activity in the latest collection window. Use this instead +// of re-broadcasting the full inbound list — it scales to 10k+ clients because +// the payload only includes active rows (typically a fraction of total). +func BroadcastClientStats(stats any) { + if hub := GetHub(); hub != nil { + hub.Broadcast(MessageTypeClientStats, stats) + } +} + +// BroadcastInbounds broadcasts inbounds list update to all connected clients. func BroadcastInbounds(inbounds any) { - hub := GetHub() - if hub != nil { + if hub := GetHub(); hub != nil { hub.Broadcast(MessageTypeInbounds, inbounds) } } -// BroadcastOutbounds broadcasts outbounds list update to all connected clients +// BroadcastOutbounds broadcasts outbounds list update to all connected clients. func BroadcastOutbounds(outbounds any) { - hub := GetHub() - if hub != nil { + if hub := GetHub(); hub != nil { hub.Broadcast(MessageTypeOutbounds, outbounds) } } -// BroadcastNotification broadcasts a system notification to all connected clients +// BroadcastNotification broadcasts a system notification to all connected clients. func BroadcastNotification(title, message, level string) { hub := GetHub() - if hub != nil { - notification := map[string]string{ - "title": title, - "message": message, - "level": level, // info, warning, error, success - } - hub.Broadcast(MessageTypeNotification, notification) + if hub == nil { + return } + hub.Broadcast(MessageTypeNotification, map[string]string{ + "title": title, + "message": message, + "level": level, + }) } -// BroadcastXrayState broadcasts Xray state change to all connected clients +// BroadcastXrayState broadcasts Xray state change to all connected clients. func BroadcastXrayState(state string, errorMsg string) { hub := GetHub() - if hub != nil { - stateUpdate := map[string]string{ - "state": state, - "errorMsg": errorMsg, - } - hub.Broadcast(MessageTypeXrayState, stateUpdate) + if hub == nil { + return } + hub.Broadcast(MessageTypeXrayState, map[string]string{ + "state": state, + "errorMsg": errorMsg, + }) } -// BroadcastInvalidate sends a lightweight invalidate signal for the given data type, -// telling connected frontends to re-fetch data via REST API. -// Use this instead of BroadcastInbounds/BroadcastOutbounds when you know the payload -// will be too large, to avoid wasting resources on serialization. +// BroadcastInvalidate sends a lightweight signal telling clients to re-fetch +// the named data type via REST. Use this when the caller already knows the +// payload is too large to push directly (e.g., 10k+ clients) to skip the +// JSON-marshal cost on the hot path. func BroadcastInvalidate(dataType MessageType) { - hub := GetHub() - if hub != nil { + if hub := GetHub(); hub != nil { hub.broadcastInvalidate(dataType) } } |
