using Luna.Channels.Abstractions; using Luna.Channels.Cli; using Luna.Channels.Web; using Luna.Core.Abstractions; using Luna.Identity.Abstractions; using Luna.Shared; using Microsoft.AspNetCore.SignalR; namespace Luna.Core.Hubs; public class ChatHub( IChannelManager channelManager, IChatHubContext hubContext, IUserIdentityService identityService) : Hub { public override Task OnConnectedAsync() { var clientType = Context.GetHttpContext()?.Request.Query["clientType"].ToString(); IChannel channel = clientType switch { "web" => new WebChannel(Context.ConnectionId, hubContext, identityService), _ => new CliChannel(Context.ConnectionId, hubContext, identityService) }; channelManager.RegisterChannel(channel); return base.OnConnectedAsync(); } public override Task OnDisconnectedAsync(Exception? exception) { channelManager.UnregisterChannel(Context.ConnectionId); return base.OnDisconnectedAsync(exception); } public async Task OnMessageReceivedAsync(ChannelMessage message) { var channel = channelManager.GetChannel(Context.ConnectionId); switch (channel) { case CliChannel cli: cli.RaiseMessageReceived(this, message); break; case WebChannel web: await web.RaiseMessageReceivedAsync(this, message); break; default: throw new InvalidOperationException( $"ChannelManager returned channel of unexpected type: {channel?.GetType().Name ?? "null"}"); } } }