Парсинг HTTP-ответа по мере его поступления - PullRequest
0 голосов
/ 18 марта 2019

Мой Web API, AAA , вызывает другой API, BBB , для получения большого массива JSON (~ 500-1000 КБ и каждого объекта по 10 КБ), ему необходимопроанализируйте массив JSON, чтобы применить к нему логику, и перенаправьте ответ на API CCC .

. Для оптимизации мне бы хотелось, чтобы в моем веб-API AAA не было хранимого ответа HTTP.содержащий большой массив JSON, поэтому массив не нужно хранить в LOH (куча больших объектов).

Я думаю, что хорошей идеей для решения этой проблемы является: вместо ожидания полного массива JSONдля загрузки возможно ли проанализировать элементы ответа по мере его поступления, чтобы я мог его проанализировать, применить к нему логику и переслать содержимое в мой API CCC ?

мой веб-API никогда не хранит большой массив JSON в памяти.Анализируя каждый объект по мере его поступления, он становится настолько маленьким, что он сохраняется в GEN 0 и очень быстро собирается GC.

Что я пробовал до сих пор:

Мой API BBBвыглядит так (упрощенно):

[HttpGet("{id}")]
public IActionResult Get(int id)
{
    var text = System.IO.File.ReadAllText("C:\\Users\\John\\generated1000objects.json");
    var deserialized = JsonConvert.DeserializeObject<object[]>(text);
    return Ok(deserialized);
}

Мой код для запроса

var httpClient = new HttpClient();

using (var request = new HttpRequestMessage(HttpMethod.Get, "https://localhost:44328/api/values/4"))
using (var response = await httpClient.SendAsync(request, HttpCompletionOption.ResponseHeadersRead))
using (Stream stream = await response.Content.ReadAsStreamAsync())
using (StreamReader sr = new StreamReader(stream))
using (JsonReader reader = new JsonTextReader(sr))
{
    reader.SupportMultipleContent = true;
    while (true)
    {
         if (!reader.Read())
         {
                break;
         }

         JsonSerializer serializer = new JsonSerializer();
         var deserialize = serializer.Deserialize<object>(reader);

         Console.WriteLine(deserialize); // HERE it prints the whole JSON Array. I was expecting to deal with one object of the array
         Console.WriteLine("#################");

     }
}

Мои ограничения:

  • Я не могу изменить API BBB , который отправляет большой массив JSON.
  • Мой API CCC не может напрямую вызвать API BBB для получения большого массива JSON

Я нахожусь на .NET Core с ASP.NET Core 2.2.

1 Ответ

0 голосов
/ 18 марта 2019

Глядя на ваше решение, если вы не ожидаете, что оно существенно увеличится в размерах, я полагаю, что вы, возможно, страдаете от попыток микрооптимизации, которая на самом деле сделает ваш процесс более хрупким, чем просто обычной обработкой.

Вы упоминаете размер записи 10 КБ, размер ответа 500-1000 КБ. В итоге получается 50-100 записей.

Я полагаю, что при попытке разобрать ответ по частям у вас будет больше трудностей, чем окажет какое-либо влияние наличия объекта в куче больших объектов. Из того, что я могу найти в различной документации, ЕДИНСТВЕННЫЙ способ синтаксического анализа документа JSON с использованием встроенной библиотеки - это анализ всего документа. Любая порция должна управляться самостоятельно.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...