Пример #1
0
        private static void ReturnAnswer(object socket)
        {
            var clientSocket = socket as Socket;

            try
            {
                var message = (Message)HelperClass.ByteArrayToObject(HelperClass.RecieveMessage(clientSocket));
                //string query = site + info + $"&mode={mode}";

                //message = ReTry(query);
                //Console.WriteLine($"{DateTime.Now.ToString(new CultureInfo("ru-RU"))} " +
                //                  $"{Thread.CurrentThread.Name} : " +
                //                  $"The message is received");
                //если пришло сообщение от другого клиента с приветсвием
                if (message.Command == Command.Greeting)
                {
                    clientSocket.Send(HelperClass.ObjectToByteArray(true));
                    var clientIpEndPoint = (IPEndPoint)clientSocket.RemoteEndPoint;
                    Client.otherClients.TryAdd(clientIpEndPoint.Address.ToString(), clientIpEndPoint);
                }
                //если пришло сообщение от другого клиента с просьбой решить подзадачу
                if (message.Command == Command.Work)
                {
                    //если этот клиент уже решает какую-то подзадачу, то говорим,
                    //что не можем пока брать на выполнение новую подзадачу
                    if (Worker.IsBusy)
                    {
                        clientSocket.Send(HelperClass.ObjectToByteArray(
                                              new Answer
                        {
                            DoneWork = false,
                        }));
                    }
                    //иначе начинаем решать новую подзадачу
                    else
                    {
                        //начинаем решать подзадачу
                        var answer = Worker.DoWork(message.Data);
                        //отправляем ответ на подзадачу
                        clientSocket.Send(HelperClass.ObjectToByteArray(answer));
                    }
                }
            }
            catch (Exception ex)
            {
                //Console.WriteLine($"{DateTime.Now.ToString(new CultureInfo("ru-RU"))} " +
                //                  $"{Thread.CurrentThread.Name} :" +
                //                  ex.Message);
                Worker.IsBusy = false;
                //message = "Извените, но на данный момент невозможно получить ответ";
                //if (handler != null && handler.Connected)
                //    handler.Send(HelperClass.ObjectToByteArray(message));
            }

            finally
            {
                if (clientSocket != null && clientSocket.Connected)
                {
                    // закрываем сокет
                    clientSocket.Shutdown(SocketShutdown.Both);
                    clientSocket.Close();
                }
            }
        }
Пример #2
0
        /// <summary>
        /// Просим другого клиента выполнить часть работы
        /// </summary>
        /// <param name="ipAddress">ip адрес другого клиента</param>
        /// <param name="port">Порт другого клиента</param>
        /// <param name="messageData">Часть работы</param>
        void SendPartWorkToClient(string ipAddress, int port, MessageData messageData)
        {
            Socket socket = null;

            try
            {
                IPEndPoint ipPoint = new IPEndPoint(IPAddress.Parse(ipAddress), port);
                socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
                // подключаемся к другому клиенту

                IAsyncResult result = socket.BeginConnect(ipAddress, port, null, null);

                bool success = result.AsyncWaitHandle.WaitOne(1000, true);

                if (socket.Connected)
                {
                    socket.EndConnect(result);
                    //отправляем клиенту данные для решения задачи
                    socket.Send(HelperClass.ObjectToByteArray(
                                    new Message
                    {
                        Command = Command.Work,
                        Data    = messageData,
                    }));
                    //добавляем в список сокетов клиентов новый
                    clientsSockets.TryAdd(ipAddress, socket);
                    clientsWorks.TryAdd(ipAddress, messageData);
                    //ждем ответ на подзадачу
                    var answer = (Answer)HelperClass.ByteArrayToObject(HelperClass.RecieveMessage(socket));
                    if (answer.DoneWork)
                    {
                        answersValues.Add(answer.Value);
                    }
                    CurrentForm.output.BeginInvoke(new InvokeDelegate(
                                                       () =>
                    {
                        CurrentForm.output.Text += $"\nКлиент {ipAddress} решил подзадачу и получил ответ {answer.Value}";
                    }));
                    Console.WriteLine($"\nКлиент {ipAddress} решил подзадачу и получил ответ {answer.Value}");
                }
                else
                {
                    //socket.Close();
                    //CurrentForm.output.BeginInvoke(new InvokeDelegate(
                    //() =>
                    //{
                    //    CurrentForm.output.Text += $"\nКлиент {ipAddress} не смог решить свою часть задачи";
                    //}));
                    //Console.WriteLine($"\nКлиент {ipAddress} не смог решить свою часть задачи");
                    ////надо переназначить часть работы кому-то другому
                    //MessageData messageData1 = null;
                    //if (clientsWorks.TryGetValue(ipAddress, out messageData1))
                    //    RunPartOwnWork(messageData1);
                }
            }
            catch
            {
                socket.Close();

                CurrentForm.output.BeginInvoke(new InvokeDelegate(
                                                   () =>
                {
                    CurrentForm.output.Text += $"\nКлиент {ipAddress} не смог решить свою часть задачи";
                }));

                Console.WriteLine($"\nКлиент {ipAddress} не смог решить свою часть задачи");
                //если другой клиент не смог взять задачу на себя
                MessageData messageData1 = null;
                if (clientsWorks.TryGetValue(ipAddress, out messageData1))
                {
                    //clientsWorks.TryRemove(ipAddress, out messageData1);
                    bool resendedToClient = false;
                    foreach (var otherClientIp in otherClients.Keys)
                    {
                        //если клиент не работает над задачей
                        if (!clientsWorks.ContainsKey(otherClientIp))
                        {
                            resendedToClient = true;
                            CurrentForm.output.BeginInvoke(new InvokeDelegate(
                                                               () =>
                            {
                                IPEndPoint endPoint = null;
                                otherClients.TryGetValue(otherClientIp, out endPoint);
                                CurrentForm.output.Text += $"\nКлиент {endPoint.Address} взял задачу клиента {ipAddress}";
                            }));
                            SendPartWorkToClient(otherClientIp, Configs.ClientPort, messageData1);
                            return;
                        }
                    }
                    if (!resendedToClient)
                    {
                        RunPartOwnWork(messageData1);
                    }
                }
            }
        }