Есть ли способ заставить MoveNext () часть цикла foreach повторить операцию применительно к результату библиотеки хранилищ Azure ListBlobs ()? - PullRequest
0 голосов
/ 24 августа 2018

У меня есть код с использованием библиотеки хранилища Azure, который выглядит следующим образом:

CloudBlobContainer container = obtainContainer();

var blobList = container.ListBlobs(options:OptionsWithLinearRetry);
foreach (var blobItem in blobList) // << exception happens here sometimes
{
     //process item
}

и в большинстве случаев работает нормально. Но иногда что-то не так с сетью, и тогда я получаю:

Microsoft.WindowsAzure.Storage.StorageException: невозможно прочитать данные из транспортного соединения: существующее соединение было принудительно закрыто удаленным хостом. ---> System.IO.IOException: невозможно прочитать данные из транспортного соединения: существующее соединение было принудительно закрыто удаленным хостом. ---> System.Net.Sockets.SocketException: существующее соединение было принудительно закрыто удаленным хостом

и стек выглядит так:

// lots of Azure Storage Library stuff here
 at Microsoft.WindowsAzure.Storage.Blob.CloudBlobContainer.<>c__DisplayClass13.<ListBlobs>b__12(IContinuationToken token)
at Microsoft.WindowsAzure.Storage.Core.Util.General.<LazyEnumerable>d__0`1.MoveNext()
// my code with foreach line here

и похоже, что foreach вызывает вызов MoveNext(), и последний завершается ошибкой при получении нового фрагмента данных.

Могу ли я как-то вызвать повторный вызов MoveNext()? Есть ли способ использовать логику try-catch-retry в цикле foreach?

1 Ответ

0 голосов
/ 24 августа 2018

Независимо от того, как повторите в следующие миллисекунды, оно будет выдавать то же исключение, пока не будет полностью закрыто.поскольку ваша учетная запись хранения достигает порогового значения / предела , указанного в хранилище Windows Azure: https://blogs.msdn.microsoft.com/windowsazurestorage/2012/11/04/cross-post-windows-azures-flat-network-storage-and-2012-scalability-targets/

На самом деле не только Azure, но и службы Google и AWS одинаковы, все они имеютпороговые значения для удаленных вызовов.

MSDN cloudblobcontainer.listblobs сообщает:

Возвращает перечисляемую коллекцию BLOB-объектов в контейнере, которая лениво .

Вы можете настроить

  1. BlobRequestOptions.RetryPolicy в следующие 0-30 секунд.
  2. BlobRequestOptions.AbsorbConditionalErrorsOnRetry
  3. BlobRequestOptions.MaximumExecutionTime

Вы обнаруживаете повторные попытки по событиям:

  1. OperationContext.GlobalRetry
  2. OperationContext.Retry

Вы также можете попробовать из Linq:

  1. .ToList()
  2. .Where(x=>x.Conditions).ToList() фильтрует бесполезные данные на стороне сервера.
  3. .Take(10) для вывода результатов на страницу, поскольку никому не нужны все результаты на 1 странице.
...