2016-05-11 8 views
0

Я использую restsharp.portable 3.1.3 в своем родном приложении Xamarin. Обычно все мои запросы отправляются одним экземпляром RestClient. Это связано с тем, что создание и удаление HttpClient - это тяжелые операции для мобильного приложения. Иногда у меня есть случаи, когда мое приложение должно отправлять несколько запросов параллельно.Портативные параллельные запросы Restsharp отправляются последовательно одним экземпляром RestClient

Например:

private async void button2_Click(object sender, EventArgs e) 
    { 
     var maxTaskCount = 3; 

     var client = new RestClient("http://jsonplaceholder.typicode.com/"); 

     var tasks = new List<Task<IRestResponse>>(); 
     for (var i = 0; i < maxTaskCount; i++) 
     { 
      var request = new RestRequest("photos"); 
      request.Method = Method.GET; 

      var task = client.Execute(request); 
      tasks.Add(task); 
     } 


     var result = await Task.WhenAll(tasks); 
    } 

Пока я профилирование моего приложения с помощью прокси-сервера (Скрипач или Чарльза) я узнал некоторые узкие места внутри restsharp.portable библиотеки. Запросы отправляются один за другим подряд. Оставшаяся резкая упаковка имеет AsyncLock класс с LockAsync метод для синхронизации всех запросов, которые отправляются одним экземпляром RestClient.

/// <summary> 
    /// Execute the given request 
    /// </summary> 
    /// <param name="request">Request to execute</param> 
    /// <returns>Response returned</returns> 
    public override async Task<IRestResponse> Execute(IRestRequest request) 
    { 
     using (await _requestGuard.LockAsync(CancellationToken.None)) 
     { 
      using (var response = await ExecuteRequest(request, CancellationToken.None)) 
      { 
       return await RestResponse.CreateResponse(this, request, response); 
      } 
     } 
    } 

Вот почему я имел проблемы с производительностью, которая была решена путем создания собственного экземпляра RestClient для каждых запросов, которые должны быть направлены параллельно.

Я понятия не имею, почему author портативного устройства RestSharp решил использовать AsyncLock внутри своего пакета. Может быть, потому, что RestClient сохраняет внутри себя какое-то состояние.

пыльник результаты моих исследований:

  1. Один экземпляр RestClient и три вызова API. Как мы видим, все 3 вызова последовательны. enter image description here
  2. Три экземпляра RestClient и три вызова API (один вызов для одного экземпляра RestClient). Как мы видим, все три вызова параллельны. enter image description here

ответ

0

HttpClient не поддерживает параллельные запросы, что является единственной причиной AsyncLock существует. Возможно, они изменили свою реализацию, но я еще не тестировал ее.

EDIT: Возможное решение вокруг этого ограничения будет заключаться в использовании пула для IRestClient экземпляров.

+0

Just FYI: [RestSharp] (https://components.xamarin.com/view/restsharp/) поддерживает параллельные запросы, поскольку он основан на HttpWebRequest/HttpWebResponse. – ZEvS

 Смежные вопросы

  • Нет связанных вопросов^_^