Conversation
| Assert.That(serverReceived, Is.EqualTo(clientMessage)); | ||
| Assert.That(clientReceived, Is.EqualTo(clientMessage)); | ||
| }); | ||
| } |
There was a problem hiding this comment.
Удивительно, но клиент и сервер в тесте даже не участвуют, тестируются TcpListener и TcpClient из стандартной библиотеки
| /// <summary> | ||
| /// Represents parsed command-line arguments for the chat application. | ||
| /// </summary> | ||
| public class Arguments |
There was a problem hiding this comment.
Думаю, что можно было сделать эту штуку record-ом или хотя бы сделать основной конструктор
| { | ||
| if (args.Length == 1) | ||
| { | ||
| return new Arguments(int.Parse(args[0]), null); |
There was a problem hiding this comment.
Стоило бы заодно проверить, принадлежит ли номер порта разрешённому диапазону, чтобы выдать пользователю понятную диагностику.
| /// </summary> | ||
| /// <param name="arguments">Arguments containing port and optional IP address.</param> | ||
| /// <returns>A <see cref="Task"/> representing the async operation.</returns> | ||
| public static async Task RunAsync(Arguments arguments) |
There was a problem hiding this comment.
Очеь желательно всё, что Async, делать отменяемым (принимать CancellationToken опциональным параметром, чтобы кому надо — могли операцию отменить). Тут и в методах ниже.
| /// <returns>Representing the asynchronous server operation.</returns> | ||
| public static async Task RunServerAsync(int port) | ||
| { | ||
| var listener = new TcpListener(IPAddress.Any, port); |
There was a problem hiding this comment.
TcpListener IDisposable, поэтому лучше его объявлять с using. Иначе из-за какого-нибудь исключения listener.Stop может не исполниться и порт останется занят до конца работы программы.
| var client = await listener.AcceptTcpClientAsync(); | ||
| lock (ConnectedClients) | ||
| { | ||
| ConnectedClients.Add(client); |
There was a problem hiding this comment.
По условию клиент всего один, так что это зря :)
|
|
||
| Console.WriteLine($"Client connected: {endpoint}"); | ||
|
|
||
| _ = Task.Run(async () => |
There was a problem hiding this comment.
А так Вы теряете ссылку на запущенную задачу, следовательно не можете её ни прервать, ни дождаться её завершения
| if (ConnectedClients.Count == 0) | ||
| { | ||
| Console.WriteLine("No clients connected. Server shutting down."); | ||
| Environment.Exit(0); |
There was a problem hiding this comment.
Это вообще не стоит использовать — вдруг сервер захотят переиспользовать в большем приложении
| { | ||
| while (true) | ||
| { | ||
| var line = Console.ReadLine(); |
There was a problem hiding this comment.
Это тоже надо было бы сделать отменяемым. Иначе клиент уже отключился, а мы сидим тут и ждём, пока пользователь что-то введёт, хотя уже давно должны были закрыть программу. У Вас эта проблема решается с помощью Environment.Exit, но это всё равно что выключатель света в доме сломался, мы дом снесли к чертям.
| } | ||
| }); | ||
|
|
||
| await Task.WhenAny(consoleTask, networkTask); |
There was a problem hiding this comment.
По-хорошему надо корректно остановить и дождаться завершения обеих задач
No description provided.