Информация об изменениях

Сообщение Re: TCP/IP скорость обмена .Net Core от 01.03.2017 9:33

Изменено 01.03.2017 9:50 Serginio1

Re: TCP/IP скорость обмена .Net Core
Сделал тест скорости с постоянным соединением и сединением на каждый запрос
using System;
using System.Collections.Generic;
using System.Text;
using System.Net;
using System.Net.Sockets;
using System.Threading.Tasks;
using System.IO;
using System.Net.NetworkInformation;
using System.Diagnostics;
using System.Linq;
namespace ClientRPC
{

    public class TCPClientConnector
    {

        TcpListener Server;

        // Будем записывать ошибки в файл
        // Нужно прописать в зависимости "System.Diagnostics.TextWriterTraceListener"
        // Файл будет рядом с этой DLL

        // Устанавливаем флаг при закрытии
        bool IsClosed = false;
        // Клиент для отпраки сообщений на сервер



        public TCPClientConnector()
        {

        }

        // Откроем порт и количество слушющих задач которое обычно равно подсоединенным устройствам
        // Нужно учитывть, что 1С обрабатывает все события последовательно ставя события в очередь
        public void Open(int Port = 6892, int CountListener = 5)
        {
            IsClosed = false;

            IPEndPoint ipEndpoint = new IPEndPoint(IPAddress.Any, Port);
            Server = new TcpListener(ipEndpoint);
            Server.Start();

            // Создадим задачи для прослушивания порта
            //При подключении клиента запустим метод ОбработкаСоединения
            // Подсмотрено здесь https://github.com/imatitya/netcorersi/blob/master/src/NETCoreRemoveServices.Core/Hosting/TcpServerListener.cs
            for (int i = 0; i < CountListener; i++)
                Server.AcceptTcpClientAsync().ContinueWith(OnConnect);

        }


        // Метод для обработки сообщения от клиента
        private void OnConnect(Task<TcpClient> task)
        {

            if (task.IsFaulted || task.IsCanceled)
            {
                // Скорее всего вызвано  Server.Stop();
                return;
            }

            // Получим клиента
            TcpClient client = task.Result;

            // И вызовем метод для обработки данных
            // 

            ExecuteMethod(client); // Соединение на каждый запрос
            //ExecuteMethod2(client);// Постоянное соединение

            // Если Server не закрыт то запускаем нового слушателя
            if (!IsClosed)
                Server.AcceptTcpClientAsync().ContinueWith(OnConnect);

        }

        private static byte[] GetByteArrayFromStream(NetworkStream ns, int Lingth)
        {
            byte[] result = new byte[Lingth];
            int ReadBytes = 0;
            while (Lingth > ReadBytes)
            {
                ReadBytes += ns.Read(result, ReadBytes, Lingth - ReadBytes);
            }

            return result;
        }

        // Соединение на каждый запрос
        private void ExecuteMethod(TcpClient client)
        {
            //    client.Client.NoDelay = true;
            using (NetworkStream ns = client.GetStream())
            {

                // Получим данные с клиента и на основании этих данных
                //Создадим ДанныеДляКлиета1С котрый кроме данных содержит 
                //TcpClient для отправки ответа
                using (var br = new BinaryReader(ns))
                {
                    var streamSize = br.ReadInt32();

                    var res = br.ReadBytes(streamSize);
                    res[0] = 4;


                    ns.Write(BitConverter.GetBytes(streamSize), 0, 4);
                    ns.Write(res, 0, streamSize);
                }

            }

        }

        // Постоянное соединение
        private void ExecuteMethod2(TcpClient client)
        {
            //    client.Client.NoDelay = true;
            NetworkStream ns = client.GetStream();
            var buffer = new byte[4];
            while (true)
            {

                buffer = GetByteArrayFromStream(ns, 4);
                var streamSize = BitConverter.ToInt32(buffer, 0);

                var res = GetByteArrayFromStream(ns, streamSize);
                res[0] = 4;
                ns.Write(BitConverter.GetBytes(streamSize), 0, 4);
                ns.Write(res, 0, res.Length);

            }



        }

    }
}



И клиент

using System;
using System.IO;
using System.Net.Sockets;
using System.Net;
namespace TestSpeedTcpClient
{


    class Program
    {
        static int repeatCount = 10000;

        static byte[] GetTestArray()
            {

            var res =new byte[40];

            for (byte i = 0; i < 40; i++)
                res[i] = i;

            return res;
        }
        static byte[] SendMessage(byte[] ms, IPEndPoint IpEndpoint)
        {

            using (var client = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp))
            {
                client.Connect(IpEndpoint);
                //      client.NoDelay = true;

                using (var ns = new NetworkStream(client))
                {
                   
                    ns.Write(BitConverter.GetBytes(ms.Length), 0, 4);
                    ns.Write(ms, 0, ms.Length);

                    using (var br = new BinaryReader(ns))
                    {
                        var streamSize = br.ReadInt32();

                        var res = br.ReadBytes(streamSize);

                        return res;
                    }

                }
            }
        }


     static   byte[] SendMessage2(byte[] ms, NetworkStream ns)
        {

            ns.Write(BitConverter.GetBytes(ms.Length), 0, 4);
            ns.Write(ms, 0, ms.Length); 
     

            var buffer = new byte[4];

            ns.Read(buffer, 0, 4);
            var streamSize = BitConverter.ToInt32(buffer, 0);
            var res = new byte[streamSize];
            ns.Read(res, 0, streamSize);

            return res;
        }


        static int TestPermanentConnection()
        {
            int count = 0;
           var IpEndpoint = new IPEndPoint(IPAddress.Parse("127.0.0.1"), 6892);
           var client = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
             client.Connect(IpEndpoint);
           var ns = new NetworkStream(client);
                    var res = GetTestArray();
            for (int i = 0; i < repeatCount; i++)
            {
                res = SendMessage2(res, ns);
                count += res[0];

            }

            return count;
        }

        static int TestOneConnection()
        {

            int count = 0;
            var IpEndpoint = new IPEndPoint(IPAddress.Parse("127.0.0.1"), 6892);

            var res = GetTestArray();
            for (int i = 0; i < repeatCount; i++)
            {
                res = SendMessage(res, IpEndpoint);
                count += res[0];

            }

            return count;
        }

        static void Main(string[] args)
        {
            Console.WriteLine("Hello Client!");

            var stopWatch = new System.Diagnostics.Stopwatch();
               stopWatch.Start();

            var res = TestOneConnection();
           // var res = TestPermanentConnection();
            stopWatch.Stop();
            var ts = stopWatch.Elapsed;
            var elapsedTime = String.Format("{0:00}:{1:00}:{2:00}.{3:00}", ts.Hours, ts.Minutes, ts.Seconds,
       ts.Milliseconds / 10, 0);


            Console.WriteLine(res);
            Console.WriteLine(elapsedTime);
            Console.ReadKey();
        }
        
    }
}


Обмен при постоянном соединении на порядок выше и составляет порядка 20 000 запросов в секунду
Re: TCP/IP скорость обмена .Net Core
Сделал тест скорости с постоянным соединением и сединением на каждый запрос
using System;
using System.Collections.Generic;
using System.Text;
using System.Net;
using System.Net.Sockets;
using System.Threading.Tasks;
using System.IO;
using System.Net.NetworkInformation;
using System.Diagnostics;
using System.Linq;
namespace ClientRPC
{

    public class TCPClientConnector
    {

        TcpListener Server;

        // Будем записывать ошибки в файл
        // Нужно прописать в зависимости "System.Diagnostics.TextWriterTraceListener"
        // Файл будет рядом с этой DLL

        // Устанавливаем флаг при закрытии
        bool IsClosed = false;
        // Клиент для отпраки сообщений на сервер



        public TCPClientConnector()
        {

        }

        // Откроем порт и количество слушющих задач которое обычно равно подсоединенным устройствам
        // Нужно учитывть, что 1С обрабатывает все события последовательно ставя события в очередь
        public void Open(int Port = 6892, int CountListener = 5)
        {
            IsClosed = false;

            IPEndPoint ipEndpoint = new IPEndPoint(IPAddress.Any, Port);
            Server = new TcpListener(ipEndpoint);
            Server.Start();

            // Создадим задачи для прослушивания порта
            //При подключении клиента запустим метод ОбработкаСоединения
            // Подсмотрено здесь https://github.com/imatitya/netcorersi/blob/master/src/NETCoreRemoveServices.Core/Hosting/TcpServerListener.cs
            for (int i = 0; i < CountListener; i++)
                Server.AcceptTcpClientAsync().ContinueWith(OnConnect);

        }


        // Метод для обработки сообщения от клиента
        private void OnConnect(Task<TcpClient> task)
        {

            if (task.IsFaulted || task.IsCanceled)
            {
                // Скорее всего вызвано  Server.Stop();
                return;
            }

            // Получим клиента
            TcpClient client = task.Result;

            // И вызовем метод для обработки данных
            // 

            ExecuteMethod(client); // Соединение на каждый запрос
            //ExecuteMethod2(client);// Постоянное соединение

            // Если Server не закрыт то запускаем нового слушателя
            if (!IsClosed)
                Server.AcceptTcpClientAsync().ContinueWith(OnConnect);

        }

        private static byte[] GetByteArrayFromStream(NetworkStream ns, int Lingth)
        {
            byte[] result = new byte[Lingth];
            int ReadBytes = 0;
            while (Lingth > ReadBytes)
            {
                ReadBytes += ns.Read(result, ReadBytes, Lingth - ReadBytes);
            }

            return result;
        }

        // Соединение на каждый запрос
        private void ExecuteMethod(TcpClient client)
        {
            //    client.Client.NoDelay = true;
            using (NetworkStream ns = client.GetStream())
            {

                // Получим данные с клиента и на основании этих данных
                //Создадим ДанныеДляКлиета1С котрый кроме данных содержит 
                //TcpClient для отправки ответа
                using (var br = new BinaryReader(ns))
                {
                    var streamSize = br.ReadInt32();

                    var res = br.ReadBytes(streamSize);
                    res[0] = 4;


                    ns.Write(BitConverter.GetBytes(streamSize), 0, 4);
                    ns.Write(res, 0, streamSize);
                }

            }

        }

        // Постоянное соединение
        private void ExecuteMethod2(TcpClient client)
        {
            //    client.Client.NoDelay = true;
            NetworkStream ns = client.GetStream();
            var buffer = new byte[4];
            while (true)
            {

                buffer = GetByteArrayFromStream(ns, 4);
                var streamSize = BitConverter.ToInt32(buffer, 0);

                var res = GetByteArrayFromStream(ns, streamSize);
                res[0] = 4;
                ns.Write(BitConverter.GetBytes(streamSize), 0, 4);
                ns.Write(res, 0, res.Length);

            }



        }

    }
}



И клиент

using System;
using System.IO;
using System.Net.Sockets;
using System.Net;
namespace TestSpeedTcpClient
{


    class Program
    {
        static int repeatCount = 10000;

        static byte[] GetTestArray()
        {

            var res = new byte[40];

            for (byte i = 0; i < 40; i++)
                res[i] = i;

            return res;
        }

        // Запрос с подключением и разрывом соединения
        static byte[] SendMessage(byte[] ms, IPEndPoint IpEndpoint)
        {

            using (var client = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp))
            {
                client.Connect(IpEndpoint);
                //      client.NoDelay = true;

                using (var ns = new NetworkStream(client))
                {

                    ns.Write(BitConverter.GetBytes(ms.Length), 0, 4);
                    ns.Write(ms, 0, ms.Length);

                    using (var br = new BinaryReader(ns))
                    {
                        var streamSize = br.ReadInt32();

                        var res = br.ReadBytes(streamSize);

                        return res;
                    }

                }
            }
        }


        // Запрос с постоянным соединением
        static byte[] SendMessage2(byte[] ms, NetworkStream ns)
        {

            ns.Write(BitConverter.GetBytes(ms.Length), 0, 4);
            ns.Write(ms, 0, ms.Length);


            var buffer = new byte[4];

            ns.Read(buffer, 0, 4);
            var streamSize = BitConverter.ToInt32(buffer, 0);
            var res = new byte[streamSize];
            ns.Read(res, 0, streamSize);

            return res;
        }


        // Тест скорости с постоянным соединением
        static int TestPermanentConnection()
        {
            int count = 0;
            var IpEndpoint = new IPEndPoint(IPAddress.Parse("127.0.0.1"), 6892);
            var client = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
            client.Connect(IpEndpoint);
            var ns = new NetworkStream(client);
            var res = GetTestArray();
            for (int i = 0; i < repeatCount; i++)
            {
                res = SendMessage2(res, ns);
                count += res[0];

            }

            return count;
        }

        // Тест скорости с подключением и разрывом соединения
        static int TestOneConnection()
        {

            int count = 0;
            var IpEndpoint = new IPEndPoint(IPAddress.Parse("127.0.0.1"), 6892);

            var res = GetTestArray();
            for (int i = 0; i < repeatCount; i++)
            {
                res = SendMessage(res, IpEndpoint);
                count += res[0];

            }

            return count;
        }

        static void Main(string[] args)
        {
            Console.WriteLine("Hello Client!");

            var stopWatch = new System.Diagnostics.Stopwatch();
            stopWatch.Start();

            var res = TestOneConnection();
            // var res = TestPermanentConnection();
            stopWatch.Stop();
            var ts = stopWatch.Elapsed;
            var elapsedTime = String.Format("{0:00}:{1:00}:{2:00}.{3:00}", ts.Hours, ts.Minutes, ts.Seconds,
       ts.Milliseconds / 10, 0);


            Console.WriteLine(res);
            Console.WriteLine(elapsedTime);
            Console.ReadKey();
        }

    }
}


Обмен при постоянном соединении на порядок выше и составляет порядка 20 000 запросов в секунду