У меня есть внешняя служба, которая работает очень быстро (ответы быстрее 50 мс в тестах SoapUI).
Но когда я использую эту службу в своем приложении .NET Core, это занимает> 500 мс на моей машине для разработки.(И более 1 секунды на рабочем сервере)
Я заметил, что Visual Studio генерирует только методы "Async" для методов внешнего сервиса.Итак, у меня есть метод doSomething()
в службе, и .NET отображает его на doSomethingAsync()
.
Чтобы вызвать этот метод, я просто добавляю ".Result" в конце, так как мне нужен ответи мне не нужно, чтобы он работал асинхронно.
var result = client.doSomethingAsync().Result;
У меня есть профилировщик (DynaTrace), который смотрит на сервер, и он показывает вызов метода SendAsync()
для вызова URL внешнего сервиса.Я не использую SendAsync()
в своем приложении.У меня даже нет экземпляра класса HttpClient
в моем коде!
Я предполагаю, что .NET каким-то образом инкапсулирует мой синхронный вызов внутри асинхронноговызов, а затем просто ожидание ответа для возобновления выполнения кода ... И я предполагаю, что это создает много накладных расходов для чего-то, что должно быть простым и быстрым.
Так что вопрос : Как я могу ускорить вызовы внешних служб в .NET Core?
Ниже приведена соответствующая часть кода:
EndpointAddress address = new EndpointAddress(baseExternalAccess.UrlService);
BasicHttpBinding binding = new BasicHttpBinding();
binding.MaxReceivedMessageSize = 2147483647;
binding.OpenTimeout = new TimeSpan(1, 0, 0);
binding.SendTimeout = new TimeSpan(1, 0, 0);
binding.Security.Mode = BasicHttpSecurityMode.Transport;
Stopwatch stopwatch = new Stopwatch();
using (MyServiceSoapClient cliente = new MyServiceSoapClient(binding,address))
{
stopwatch.Reset();
stopwatch.Start();
var result = cliente.doSomethingAsync().Result;
stopwatch.Stop();
logger.Information("Time: " + stopwatch.ElapsedMilliseconds.ToString() + "ms");
}
Редактировать: КомуПоясняя проблему, я создаю два новых проекта с нуля.Один использует .NET Core, а другой - .NET Framework.
.NET Core
- Щелкните правой кнопкой мыши по проекту
- Добавить -> Подключенная служба
- Выберите «Поставщик ссылок на веб-службы Microsoft WCF»
- Сообщите URI wsdl службы, нажмите GO
- Сообщите пространство имен, нажмите Далее
- Ничего не измените, нажмите Готово
- Подождите, пока Visual Studio обнаружит службу и создаст ее содержимое.
.NET Framework
- Щелкните правой кнопкой мыши «Ссылки» -> Добавить ссылку на службу ...
- В поле «Адрес» сообщите wsdl URL службы, нажмите GO.
- Сообщите пространство имен, нажмите «Дополнительно»
- Снимите флажок «Разрешить генерацию асинхронных операций», нажмите «ОК».
- Нажмите «ОК» и подождите, пока VS создаст его материал.
Затем в обоих проектах:Я сделал простой вызов того же метода, используя те же параметры.На самом деле код практически такой же, единственное отличие состоит в том, что в версии .NET Core имя метода равно «doSomethingAsync ()», и я должен использовать «.Result» после имени метода, тогда как в .NETВерсия платформы, имя метода - doSomething (), и я могу вызвать его напрямую.
Edit 2: Каждый раз, когда я запускаю этот тест, я получаю похожие результаты ... Первый вызовк методу обслуживания всегда. ~ 700 мс быстрее в .NET Framework версии.Следующие 9 вызовов имеют схожую синхронизацию (но .NET Framework всегда немного быстрее).
В моей программе мне просто нужно вызвать службу один раз, поэтому для меня важно только время первого вызова.
Редактировать 3: Хорошо, похоже, что .NET Core имеет некоторую задержку при доступе к веб-службам.
Я сделал четыре версии консольного приложения C #, которое только делает10 запросов к этой внешней службе и измерение времени с помощью секундомера:
- .NET Framework 2.0 (с использованием веб-ссылки)
- .NET Framework 4.6.1 (с использованием ссылки на службу WCF)
- .NET Core 2.1 (с использованием справки по веб-службе WCF)
- .NET Core 2.2 (с использованием справки по веб-службе WCF)
Вот результаты:
Test .NET Framework 2.0 Web Reference
Time: 1502ms
Time: 762ms
Time: 693ms
Time: 728ms
Time: 763ms
Time: 644ms
Time: 845ms
Time: 688ms
Time: 667ms
Time: 676ms
Total time: 7993ms
Test .NET Framework 4.6.1 WCF Reference
Time: 1770ms
Time: 675ms
Time: 619ms
Time: 644ms
Time: 895ms
Time: 671ms
Time: 611ms
Time: 702ms
Time: 655ms
Time: 741ms
Total time: 8251ms
Test .NET Core 2.1 WCF Reference
Time: 2984ms
Time: 759ms
Time: 899ms
Time: 874ms
Time: 756ms
Time: 792ms
Time: 922ms
Time: 1001ms
Time: 767ms
Time: 679ms
Total time: 10810ms
Test .NET Core 2.2 WCF Reference
Time: 3167ms
Time: 796ms
Time: 707ms
Time: 732ms
Time: 929ms
Time: 828ms
Time: 775ms
Time: 847ms
Time: 957ms
Time: 884ms
Total time: 10877ms
Как показывают результаты, самая большая проблема связана с первым запросом.Это занимает больше времени, чем остальные 9 запросов, и последние 9 запросов имеют одинаковую синхронизацию во всех тестах te (но .NET Core все еще немного медленнее).
Мое приложение делает только один запрос к веб-службе, поэтомудля меня важен только первый звонок.
Итак, мои выводы заключаются в том, что .NET Core работает медленно с веб-службами WCF.