diff --git a/Govor.API.Tests/Govor.API.Tests.csproj b/Govor.API.Tests/Govor.API.Tests.csproj index b74c1ac..2ef9646 100644 --- a/Govor.API.Tests/Govor.API.Tests.csproj +++ b/Govor.API.Tests/Govor.API.Tests.csproj @@ -27,8 +27,4 @@ - - - - diff --git a/Govor.API/Hubs/ChatsHub.cs b/Govor.API/Hubs/ChatsHub.cs index f0f509c..af8c6e3 100644 --- a/Govor.API/Hubs/ChatsHub.cs +++ b/Govor.API/Hubs/ChatsHub.cs @@ -87,15 +87,15 @@ public class ChatsHub : Hub public async Task Send(MessageRequest request) { + var senderId = GetUserId(); + if (string.IsNullOrWhiteSpace(request.EncryptedContent) && (request.MediaAttachments == null || !request.MediaAttachments.Any())) { - _logger.LogWarning("Empty message (no content and no attachments) received from user {UserId}", - GetUserId()); + _logger.LogWarning("Empty message (no content and no attachments) received from user {UserId}", senderId); throw new ArgumentException("Message cannot be empty (must have content or attachments)."); } - var senderId = GetUserId(); _logger.LogInformation("Message send initiated by {SenderId} to {RecipientId} of type {RecipientType}", senderId, request.RecipientId, request.RecipientType); @@ -150,9 +150,72 @@ public class ChatsHub : Hub "Message {MessageId} sent successfully from {SenderId} to {RecipientId} ({RecipientType})", result.Message.Id, senderId, request.RecipientId, request.RecipientType); } - + public async Task Remove(RemoveMessageRequest request) { + var removerId = GetUserId(); + _logger.LogInformation("Message removal initiated by {RemoverId} for message {MessageId}", removerId, request.MessageId); + + var removeParams = new DeleteMessage( + DeleterId: removerId, + MessageId: request.MessageId + ); + + try + { + var result = await _messageCommandService.DeleteMessageAsync(removeParams); + if (!result.IsSuccess) + { + _logger.LogError(result.Exception, "Failed to remove message {MessageId} by {RemoverId}. Error: {ErrorMessage}", request.MessageId, removerId, result.Exception?.Message ?? "Unknown error"); + if (result.Exception != null) throw result.Exception; + throw new HubException("Failed to remove message."); + } + + var originalMessage = result.OriginalMessage; // Assuming service returns this + if (originalMessage == null) + { + _logger.LogError("DeleteMessageAsync succeeded but did not return the original message details for message {MessageId}", request.MessageId); + throw new HubException("Failed to process message deletion due to missing message details."); + } + + var removalNotification = new MessageRemovedResponse + { + MessageId = request.MessageId, + SenderId = originalMessage.SenderId, + RecipientId = originalMessage.RecipientId, + RecipientType = originalMessage.RecipientType + }; + + // Notify relevant clients + if (originalMessage.RecipientType == RecipientType.User) + { + await Clients.Group(originalMessage.SenderId.ToString()).SendAsync("MessageRemoved", removalNotification); + if (originalMessage.SenderId != originalMessage.RecipientId) + { + await Clients.Group(originalMessage.RecipientId.ToString()).SendAsync("MessageRemoved", removalNotification); + } + } + else if (originalMessage.RecipientType == RecipientType.Group) + { + await Clients.Group($"group_{originalMessage.RecipientId}").SendAsync("MessageRemoved", removalNotification); + } + _logger.LogInformation("Message {MessageId} removed successfully by {RemoverId}", request.MessageId, removerId); + } + catch (UnauthorizedAccessException ex) + { + _logger.LogWarning(ex, "Unauthorized attempt to remove message {MessageId} by user {RemoverId}", request.MessageId, removerId); + throw new HubException("You are not authorized to remove this message.", ex); + } + catch (KeyNotFoundException ex) // Or a custom NotFoundException + { + _logger.LogWarning(ex, "Attempt to remove non-existent message {MessageId} by user {RemoverId}", request.MessageId, removerId); + throw new HubException("Message not found.", ex); + } + catch (Exception ex) + { + _logger.LogError(ex, "Error removing message {MessageId} by {RemoverId}", request.MessageId, removerId); + throw new HubException("An error occurred while removing the message.", ex); + } } public async Task Edit(EditMessageRequest request) diff --git a/Govor.API/Program.cs b/Govor.API/Program.cs index 8f285d3..3232205 100644 --- a/Govor.API/Program.cs +++ b/Govor.API/Program.cs @@ -121,8 +121,8 @@ app.UseAuthorization(); app.MapControllers(); -app.MapHub("/api/chats"); -app.MapHub("/api/friends"); +app.MapHub("/hubs/friends"); +app.MapHub("/hubs/friends"); app.MapSwagger().RequireAuthorization(); diff --git a/Govor.Console/Commands/AcceptFriendRequestCommand.cs b/Govor.Console/Commands/AcceptFriendRequestCommand.cs index 5a54b82..a81be53 100644 --- a/Govor.Console/Commands/AcceptFriendRequestCommand.cs +++ b/Govor.Console/Commands/AcceptFriendRequestCommand.cs @@ -1,5 +1,6 @@ using System; using System.Threading.Tasks; +using Microsoft.AspNetCore.SignalR.Client; namespace Govor.ConsoleClient.Commands { @@ -24,7 +25,7 @@ namespace Govor.ConsoleClient.Commands try { // API uses Hub for this: AcceptFriendRequest(Guid friendshipId) - await HubConnection.InvokeAsync("AcceptFriendRequest", friendshipId); + await HubConnection.InvokeAsync("AcceptRequest", friendshipId); Console.WriteLine("Заявка в друзья принята."); } catch (Exception ex) diff --git a/Govor.Console/Commands/AdminListAllFriendshipsCommand.cs b/Govor.Console/Commands/AdminListAllFriendshipsCommand.cs index 24aef5a..226c547 100644 --- a/Govor.Console/Commands/AdminListAllFriendshipsCommand.cs +++ b/Govor.Console/Commands/AdminListAllFriendshipsCommand.cs @@ -3,6 +3,7 @@ using System.Collections.Generic; using System.Linq; using System.Net.Http; using System.Net.Http.Json; +using System.Text.Json; using System.Threading.Tasks; using Govor.Contracts.DTOs; // Required for FriendshipDto @@ -19,15 +20,12 @@ namespace Govor.ConsoleClient.Commands Console.WriteLine("Получение всех дружеских связей (только для администраторов)..."); try { - var response = await HttpClientService.GetAsync("api/admin/Friendships"); - if (response.StatusCode == System.Net.HttpStatusCode.Forbidden) - { - Console.WriteLine("[Ошибка] Доступ запрещен. Эта команда только для администраторов."); - return; - } - response.EnsureSuccessStatusCode(); + var json = await HttpClientService.GetAsync("api/admin/Friendships"); - var friendships = await response.Content.ReadFromJsonAsync>(); + var friendships = JsonSerializer.Deserialize>(json, new JsonSerializerOptions + { + PropertyNameCaseInsensitive = true + }); if (friendships != null && friendships.Any()) { diff --git a/Govor.Console/Commands/AdminListUserFriendshipsCommand.cs b/Govor.Console/Commands/AdminListUserFriendshipsCommand.cs index 3b81970..96b4539 100644 --- a/Govor.Console/Commands/AdminListUserFriendshipsCommand.cs +++ b/Govor.Console/Commands/AdminListUserFriendshipsCommand.cs @@ -3,6 +3,7 @@ using System.Collections.Generic; using System.Linq; using System.Net.Http; using System.Net.Http.Json; +using System.Text.Json; using System.Threading.Tasks; using Govor.Contracts.DTOs; // Required for FriendshipDto @@ -30,14 +31,8 @@ namespace Govor.ConsoleClient.Commands try { var response = await HttpClientService.GetAsync($"api/admin/Friendships/{userId}"); - if (response.StatusCode == System.Net.HttpStatusCode.Forbidden) - { - Console.WriteLine("[Ошибка] Доступ запрещен. Эта команда только для администраторов."); - return; - } - response.EnsureSuccessStatusCode(); - var friendships = await response.Content.ReadFromJsonAsync>(); + var friendships = JsonSerializer.Deserialize>(response); if (friendships != null && friendships.Any()) { diff --git a/Govor.Console/Commands/AdminRemoveFriendshipCommand.cs b/Govor.Console/Commands/AdminRemoveFriendshipCommand.cs index 07fdea2..aa55ff9 100644 --- a/Govor.Console/Commands/AdminRemoveFriendshipCommand.cs +++ b/Govor.Console/Commands/AdminRemoveFriendshipCommand.cs @@ -32,14 +32,7 @@ namespace Govor.ConsoleClient.Commands // Let's assume query parameter for now as it's simpler for HttpPost. var response = await HttpClientService.PostAsync($"api/admin/Friendships?Id={friendshipId}", null); - - if (response.StatusCode == System.Net.HttpStatusCode.Forbidden) - { - Console.WriteLine("[Ошибка] Доступ запрещен. Эта команда только для администраторов."); - return; - } - response.EnsureSuccessStatusCode(); - + Console.WriteLine($"Дружеская связь {friendshipId} успешно удалена."); } catch (HttpRequestException httpEx) when (httpEx.StatusCode == System.Net.HttpStatusCode.Forbidden) diff --git a/Govor.Console/Commands/BaseCommand.cs b/Govor.Console/Commands/BaseCommand.cs index 358b48d..9706fbe 100644 --- a/Govor.Console/Commands/BaseCommand.cs +++ b/Govor.Console/Commands/BaseCommand.cs @@ -1,3 +1,4 @@ +using Microsoft.AspNetCore.SignalR.Client; using System; using System.Threading.Tasks; @@ -6,13 +7,13 @@ namespace Govor.ConsoleClient.Commands public abstract class BaseCommand : ICommand { protected static FriendsClient? FriendsClient { get; private set; } - protected static HttpClientService HttpClientService { get; private set; } - protected static Func GetAuthToken { get; private set; } - protected static Action SetAuthToken { get; private set; } - protected static Func InitializeHubConnectionAsync { get; private set; } - protected static Microsoft.AspNetCore.SignalR.Client.HubConnection? HubConnection => _hubConnection?.Invoke(); - private static Func _hubConnection; - + protected static HttpClientService HttpClientService { get; private set; } = null!; + protected static Func GetAuthToken { get; private set; } = null!; + protected static Action SetAuthToken { get; private set; } = null!; + protected static Func InitializeHubConnectionAsync { get; private set; } = null!; + protected static HubConnection HubConnection => _getHubConnection?.Invoke(); + + private static Func _getHubConnection = null!; public static void InitializeServices( FriendsClient? friendsClient, @@ -20,43 +21,42 @@ namespace Govor.ConsoleClient.Commands Func getAuthToken, Action setAuthToken, Func initializeHubConnectionAsync, - Func hubConnection) + Func getHubConnection) { FriendsClient = friendsClient; HttpClientService = httpClientService; GetAuthToken = getAuthToken; SetAuthToken = setAuthToken; InitializeHubConnectionAsync = initializeHubConnectionAsync; - _hubConnection = hubConnection; + _getHubConnection = getHubConnection; } public abstract Task ExecuteAsync(string? argument); public abstract string GetHelp(); - protected boolEnsureLoggedIn() + protected bool EnsureLoggedIn() { if (GetAuthToken() == null) { - System.Console.WriteLine("[Ошибка] Сначала войдите в систему. Используйте /login или /reg."); + Console.WriteLine("[Ошибка] Сначала войдите в систему. Используйте /login или /reg."); return false; } - if (FriendsClient == null && !(this is LoginCommand || this is RegisterCommand)) // FriendsClient might not be needed for auth commands + + if (FriendsClient == null && !(this is LoginCommand || this is RegisterCommand)) { - // Attempt to re-initialize FriendsClient if token exists but client is null - // This can happen if the app was closed and token was persisted, but client was not re-instantiated. - // However, the current setup in Program.cs initializes FriendsClient after login/reg. - // This check is more of a safeguard. - System.Console.WriteLine("[Ошибка] Клиент для работы с друзьями не инициализирован. Попробуйте войти снова."); - return false; + Console.WriteLine("[Ошибка] Клиент для работы с друзьями не инициализирован. Попробуйте войти снова."); + return false; } + return true; } - protected boolEnsureHubConnection() + protected bool EnsureHubConnection() { - if (HubConnection == null || HubConnection.State != Microsoft.AspNetCore.SignalR.Client.HubConnectionState.Connected) + var hub = _getHubConnection?.Invoke(); + if (hub == null || hub.State != HubConnectionState.Connected) { - System.Console.WriteLine("[Ошибка] SignalR соединение не установлено. Попробуйте войти снова или проверьте соединение."); + Console.WriteLine("[Ошибка] SignalR соединение не установлено. Попробуйте войти снова или проверьте соединение."); return false; } return true; diff --git a/Govor.Console/Commands/BlockUserCommand.cs b/Govor.Console/Commands/BlockUserCommand.cs index 766bef5..bf83a39 100644 --- a/Govor.Console/Commands/BlockUserCommand.cs +++ b/Govor.Console/Commands/BlockUserCommand.cs @@ -1,5 +1,6 @@ using System; using System.Threading.Tasks; +using Microsoft.AspNetCore.SignalR.Client; namespace Govor.ConsoleClient.Commands { diff --git a/Govor.Console/Commands/ListOutgoingRequestsCommand.cs b/Govor.Console/Commands/ListOutgoingRequestsCommand.cs index 992dd60..ffa272d 100644 --- a/Govor.Console/Commands/ListOutgoingRequestsCommand.cs +++ b/Govor.Console/Commands/ListOutgoingRequestsCommand.cs @@ -2,6 +2,7 @@ using System; using System.Linq; using System.Net.Http; using System.Net.Http.Json; +using System.Text.Json; using System.Threading.Tasks; using Govor.Contracts.DTOs; // Required for FriendshipDto @@ -17,10 +18,12 @@ namespace Govor.ConsoleClient.Commands { // This functionality maps to GET api/friends/responses in FriendsRequestQueryController // FriendsClient doesn't have a dedicated method, so we use HttpClientService or direct HttpClient - var response = await HttpClientService.GetAsync("api/friends/responses"); - response.EnsureSuccessStatusCode(); + var json = await HttpClientService.GetAsync("api/friends/responses"); - var requests = await response.Content.ReadFromJsonAsync>(); + var requests = JsonSerializer.Deserialize>(json, new JsonSerializerOptions + { + PropertyNameCaseInsensitive = true + }); if (requests != null && requests.Any()) { diff --git a/Govor.Console/Commands/LoginCommand.cs b/Govor.Console/Commands/LoginCommand.cs index 94b8665..9f2d017 100644 --- a/Govor.Console/Commands/LoginCommand.cs +++ b/Govor.Console/Commands/LoginCommand.cs @@ -30,8 +30,9 @@ namespace Govor.ConsoleClient.Commands sharedClient.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", authToken); var friendsClient = new FriendsClient(sharedClient); - // Re-initialize services in BaseCommand with the new FriendsClient - InitializeServices(friendsClient, HttpClientService, GetAuthToken, SetAuthToken, InitializeHubConnectionAsync, HubConnection); + + + Program.UpdateFriendsClient(friendsClient); // <-- единственный нужный вызов await InitializeHubConnectionAsync(); Console.WriteLine("[Успех] Вход выполнен. Токен сохранен."); diff --git a/Govor.Console/Commands/RegisterCommand.cs b/Govor.Console/Commands/RegisterCommand.cs index c1bcfc0..2dd84e7 100644 --- a/Govor.Console/Commands/RegisterCommand.cs +++ b/Govor.Console/Commands/RegisterCommand.cs @@ -34,7 +34,7 @@ namespace Govor.ConsoleClient.Commands var friendsClient = new FriendsClient(sharedClient); // Re-initialize services in BaseCommand with the new FriendsClient - InitializeServices(friendsClient, HttpClientService, GetAuthToken, SetAuthToken, InitializeHubConnectionAsync, HubConnection); + Program.UpdateFriendsClient(friendsClient); // <-- единственный нужный вызов await InitializeHubConnectionAsync(); Console.WriteLine("[Успех] Регистрация завершена. Токен сохранен."); diff --git a/Govor.Console/Commands/RejectFriendRequestCommand.cs b/Govor.Console/Commands/RejectFriendRequestCommand.cs index f2a0f83..afd9673 100644 --- a/Govor.Console/Commands/RejectFriendRequestCommand.cs +++ b/Govor.Console/Commands/RejectFriendRequestCommand.cs @@ -1,5 +1,6 @@ using System; using System.Threading.Tasks; +using Microsoft.AspNetCore.SignalR.Client; namespace Govor.ConsoleClient.Commands { @@ -25,7 +26,7 @@ namespace Govor.ConsoleClient.Commands { // API uses Hub for this: RejectFriendRequest(Guid friendshipId) // Located in Govor.API/Hubs/FriendsHub.cs - await HubConnection.InvokeAsync("RejectFriendRequest", friendshipId); + await HubConnection.InvokeAsync("RejectRequest", friendshipId); Console.WriteLine("Заявка в друзья отклонена."); } catch (Exception ex) diff --git a/Govor.Console/Commands/SendFriendRequestCommand.cs b/Govor.Console/Commands/SendFriendRequestCommand.cs index 62aae31..62c65fe 100644 --- a/Govor.Console/Commands/SendFriendRequestCommand.cs +++ b/Govor.Console/Commands/SendFriendRequestCommand.cs @@ -1,5 +1,6 @@ using System; using System.Threading.Tasks; +using Microsoft.AspNetCore.SignalR.Client; namespace Govor.ConsoleClient.Commands { @@ -24,7 +25,7 @@ namespace Govor.ConsoleClient.Commands try { // API uses Hub for this: SendFriendRequest(Guid targetUserId) - await HubConnection.InvokeAsync("SendFriendRequest", targetUserId); + await HubConnection.InvokeAsync("SendRequest", targetUserId); Console.WriteLine("Запрос в друзья отправлен."); } catch (Exception ex) diff --git a/Govor.Console/Commands/UnblockUserCommand.cs b/Govor.Console/Commands/UnblockUserCommand.cs index bc2dae4..5fa17fc 100644 --- a/Govor.Console/Commands/UnblockUserCommand.cs +++ b/Govor.Console/Commands/UnblockUserCommand.cs @@ -1,5 +1,6 @@ using System; using System.Threading.Tasks; +using Microsoft.AspNetCore.SignalR.Client; namespace Govor.ConsoleClient.Commands { diff --git a/Govor.Console/FriendsHubClient.cs b/Govor.Console/FriendsHubClient.cs new file mode 100644 index 0000000..f8667d2 --- /dev/null +++ b/Govor.Console/FriendsHubClient.cs @@ -0,0 +1,157 @@ +using System; +using System.Threading.Tasks; +using Microsoft.AspNetCore.SignalR; +using Microsoft.AspNetCore.SignalR.Client; + +class FriendsHubClient +{ + private readonly HubConnection _connection; + + public FriendsHubClient(string hubUrl, string jwtToken) + { + _connection = new HubConnectionBuilder() + .WithUrl(hubUrl, options => + { + options.AccessTokenProvider = () => Task.FromResult(jwtToken); + }) + .WithAutomaticReconnect() + .Build(); + + // Подписка на события от сервера + _connection.On("FriendRequestReceived", OnFriendRequestReceived); + _connection.On("FriendRequestAccepted", OnFriendRequestAccepted); + _connection.On("FriendRequestRejected", OnFriendRequestRejected); + } + + private void OnFriendRequestReceived(Guid userId) + { + Console.WriteLine($"[Event] Получен запрос в друзья от пользователя: {userId}"); + } + + private void OnFriendRequestAccepted(Guid friendshipId) + { + Console.WriteLine($"[Event] Запрос в друзья принят. ID дружбы: {friendshipId}"); + } + + private void OnFriendRequestRejected(Guid friendshipId) + { + Console.WriteLine($"[Event] Запрос в друзья отклонён. ID дружбы: {friendshipId}"); + } + + public async Task StartAsync() + { + await _connection.StartAsync(); + Console.WriteLine("Подключено к FriendsHub"); + } + + public async Task StopAsync() + { + await _connection.StopAsync(); + Console.WriteLine("Отключено от FriendsHub"); + } + + public async Task SendRequest(Guid targetUserId) + { + try + { + await _connection.InvokeAsync("SendRequest", targetUserId); + Console.WriteLine($"Запрос на добавление в друзья отправлен пользователю {targetUserId}"); + } + catch (HubException ex) + { + Console.WriteLine($"Ошибка при отправке запроса: {ex.Message}"); + } + } + + public async Task AcceptRequest(Guid friendshipId) + { + try + { + await _connection.InvokeAsync("AcceptRequest", friendshipId); + Console.WriteLine($"Запрос в друзья с ID {friendshipId} принят"); + } + catch (HubException ex) + { + Console.WriteLine($"Ошибка при принятии запроса: {ex.Message}"); + } + } + + public async Task RejectRequest(Guid friendshipId) + { + try + { + await _connection.InvokeAsync("RejectRequest", friendshipId); + Console.WriteLine($"Запрос в друзья с ID {friendshipId} отклонён"); + } + catch (HubException ex) + { + Console.WriteLine($"Ошибка при отклонении запроса: {ex.Message}"); + } + } +} + +class Program +{ + static async Task TestMain(string[] args) + { + // Адрес хаба SignalR + string hubUrl = "https://yourserver.com/api/friends"; + + // JWT токен для аутентификации (замени на настоящий) + string jwtToken = "your_jwt_token_here"; + + var client = new FriendsHubClient(hubUrl, jwtToken); + + await client.StartAsync(); + + Console.WriteLine("Команды:"); + Console.WriteLine("send - Отправить запрос в друзья"); + Console.WriteLine("accept - Принять запрос"); + Console.WriteLine("reject - Отклонить запрос"); + Console.WriteLine("exit - Выйти"); + + while (true) + { + Console.Write("> "); + var input = Console.ReadLine(); + if (string.IsNullOrWhiteSpace(input)) + continue; + + var parts = input.Split(' ', 2, StringSplitOptions.RemoveEmptyEntries); + var command = parts[0].ToLowerInvariant(); + + if (command == "exit") + break; + + if (parts.Length < 2) + { + Console.WriteLine("Ошибка: не хватает аргументов"); + continue; + } + + if (!Guid.TryParse(parts[1], out var id)) + { + Console.WriteLine("Ошибка: некорректный GUID"); + continue; + } + + switch (command) + { + case "send": + await client.SendRequest(id); + break; + case "accept": + await client.AcceptRequest(id); + break; + case "reject": + await client.RejectRequest(id); + break; + default: + Console.WriteLine("Неизвестная команда"); + break; + } + } + + await client.StopAsync(); + } +} diff --git a/Govor.Console/HttpClientService.cs b/Govor.Console/HttpClientService.cs index 93aa10f..9482b92 100644 --- a/Govor.Console/HttpClientService.cs +++ b/Govor.Console/HttpClientService.cs @@ -18,6 +18,28 @@ namespace Govor.ConsoleClient }; } + public string GetBaseUrl() => _client.BaseAddress?.ToString() ?? string.Empty; + + public async Task GetAsync(string uri) + { + var response = await _client.GetAsync(uri); + response.EnsureSuccessStatusCode(); + return await response.Content.ReadAsStringAsync(); + } + + public async Task PostAsync(string uri, object? payload = null) + { + HttpResponseMessage response; + + if (payload is null) + response = await _client.PostAsync(uri, null); + else + response = await _client.PostAsJsonAsync(uri, payload); + + response.EnsureSuccessStatusCode(); + return await response.Content.ReadAsStringAsync(); + } + public async Task RegisterAsync(string username, string password, string inviteCode) { var request = new RegistrationRequest diff --git a/Govor.Console/Program.cs b/Govor.Console/Program.cs index 1c8760c..4609304 100644 --- a/Govor.Console/Program.cs +++ b/Govor.Console/Program.cs @@ -9,6 +9,7 @@ using System.Threading.Tasks; using Govor.ConsoleClient.Commands; using Govor.Contracts.Requests.SignalR; using Govor.Contracts.Responses.SignalR; +using Govor.Core.Models; /*==================================== *Личные сообщения| Егор @@ -194,7 +195,7 @@ namespace Govor.ConsoleClient } _hubConnection = new HubConnectionBuilder() - .WithUrl($"{baseUrl}/api/chats", options => + .WithUrl($"{baseUrl}/hubs/chats", options => { options.AccessTokenProvider = () => Task.FromResult(AuthToken); }) @@ -203,7 +204,7 @@ namespace Govor.ConsoleClient _hubConnection.On("ReceiveMessage", (message) => { var myId = GetMyUserId(); - var senderName = message.SenderId == myId ? "Ты" : CurrentChatUser ?? message.SenderUsername ?? "Неизвестно"; + var senderName = message.SenderId == myId ? "Ты" : CurrentChatUser ?? message.SenderId.ToString() ?? "Неизвестно"; var displayMessage = $"[{message.SentAt:HH:mm}] {senderName} >> {message.EncryptedContent}"; // Determine chat key based on sender/recipient, ensuring consistency @@ -230,7 +231,7 @@ namespace Govor.ConsoleClient } else // Notification for message not in the current chat { - Console.WriteLine($"\n[Новое сообщение от {message.SenderUsername ?? message.SenderId.ToString()}]: {message.EncryptedContent}"); + Console.WriteLine($"\n[Новое сообщение от {message.SenderId.ToString()}]: {message.EncryptedContent}"); Console.Write(CurrentChatUser == null ? "/> " : ">> "); // Re-display prompt } }); @@ -331,7 +332,7 @@ namespace Govor.ConsoleClient { RecipientId = CurrentChatUserId, EncryptedContent = messageContent, - RecipientType = RecipientType.User, + RecipientType = RecipientType.User }; try diff --git a/Govor.Contracts/Responses/SignalR/MessageRemovedResponse.cs b/Govor.Contracts/Responses/SignalR/MessageRemovedResponse.cs new file mode 100644 index 0000000..2fd3ff8 --- /dev/null +++ b/Govor.Contracts/Responses/SignalR/MessageRemovedResponse.cs @@ -0,0 +1,11 @@ +using Govor.Core.Models; + +namespace Govor.Contracts.Responses.SignalR; + +public class MessageRemovedResponse +{ + public Guid MessageId { get; set; } + public Guid SenderId { get; set; } + public Guid RecipientId { get; set; } + public RecipientType RecipientType { get; set; } +} \ No newline at end of file