< Summary - Kestrun — Combined Coverage

Information
Class: Kestrun.SignalR.RealtimeBroadcaster
Assembly: Kestrun
File(s): /home/runner/work/Kestrun/Kestrun/src/CSharp/Kestrun/SignalR/RealtimeBroadcaster.cs
Tag: Kestrun/Kestrun@0d738bf294e6281b936d031e1979d928007495ff
Line coverage
100%
Covered lines: 42
Uncovered lines: 0
Coverable lines: 42
Total lines: 81
Line coverage: 100%
Branch coverage
N/A
Covered branches: 0
Total branches: 0
Branch coverage: N/A
Method coverage

Feature is only available for sponsors

Upgrade to PRO version

Coverage history

Coverage history 0 25 50 75 100 10/15/2025 - 21:27:26 Line coverage: 0% (0/42) Total lines: 81 Tag: Kestrun/Kestrun@c33ec02a85e4f8d6061aeaab5a5e8c3a8b66559412/15/2025 - 18:44:50 Line coverage: 100% (42/42) Total lines: 81 Tag: Kestrun/Kestrun@6b9e56ea2de904fc3597033ef0f9bc7839d5d618

Metrics

MethodBranch coverage Crap Score Cyclomatic complexity Line coverage
.ctor(...)100%11100%
BroadcastLogAsync()100%11100%
BroadcastEventAsync()100%11100%
BroadcastToGroupAsync()100%11100%

File(s)

/home/runner/work/Kestrun/Kestrun/src/CSharp/Kestrun/SignalR/RealtimeBroadcaster.cs

#LineLine coverage
 1using Microsoft.AspNetCore.SignalR;
 2using Kestrun.Utilities.Json;
 3
 4namespace Kestrun.SignalR;
 5
 6/// <summary>
 7/// Default implementation of <see cref="IRealtimeBroadcaster"/> that broadcasts messages via SignalR.
 8/// </summary>
 9/// <remarks>
 10/// Initializes a new instance of the <see cref="RealtimeBroadcaster"/> class.
 11/// </remarks>
 12/// <param name="hubContext">The SignalR hub context for KestrunHub.</param>
 13/// <param name="logger">The Serilog logger instance.</param>
 2314public class RealtimeBroadcaster(IHubContext<KestrunHub> hubContext, Serilog.ILogger logger) : IRealtimeBroadcaster
 15{
 2316    private readonly IHubContext<KestrunHub> _hubContext = hubContext;
 2317    private readonly Serilog.ILogger _logger = logger;
 18
 19    /// <inheritdoc/>
 20    public async Task BroadcastLogAsync(string level, string message, CancellationToken cancellationToken = default)
 21    {
 22        try
 23        {
 1124            await _hubContext.Clients.All.SendAsync(
 1125                "ReceiveLog",
 1126                new
 1127                {
 1128                    level,
 1129                    message,
 1130                    timestamp = DateTime.UtcNow
 1131                },
 1132                cancellationToken);
 33
 934            _logger.Debug("Broadcasted log message: {Level} - {Message}", level, message);
 935        }
 236        catch (Exception ex)
 37        {
 238            _logger.Error(ex, "Failed to broadcast log message: {Level} - {Message}", level, message);
 239        }
 1140    }
 41
 42    /// <inheritdoc/>
 43    public async Task BroadcastEventAsync(string eventName, object? data, CancellationToken cancellationToken = default)
 44    {
 45        try
 46        {
 47            // Sanitize data to avoid object cycles (PSObject graphs, etc.)
 748            var safe = PayloadSanitizer.Sanitize(data);
 749            await _hubContext.Clients.All.SendAsync(
 750                "ReceiveEvent",
 751                new
 752                {
 753                    eventName,
 754                    data = safe,
 755                    timestamp = DateTime.UtcNow
 756                },
 757                cancellationToken);
 58
 559            _logger.Debug("Broadcasted event: {EventName}", eventName);
 560        }
 261        catch (Exception ex)
 62        {
 263            _logger.Error(ex, "Failed to broadcast event: {EventName}", eventName);
 264        }
 765    }
 66
 67    /// <inheritdoc/>
 68    public async Task BroadcastToGroupAsync(string groupName, string method, object? message, CancellationToken cancella
 69    {
 70        try
 71        {
 972            var safe = PayloadSanitizer.Sanitize(message);
 973            await _hubContext.Clients.Group(groupName).SendAsync(method, safe, cancellationToken);
 774            _logger.Debug("Broadcasted message to group {GroupName} via method {Method}", groupName, method);
 775        }
 276        catch (Exception ex)
 77        {
 278            _logger.Error(ex, "Failed to broadcast to group {GroupName}", groupName);
 279        }
 980    }
 81}