1

Мне нужно сгенерировать довольно много отчетов, и отчет может занять около 5 минут, большой объем данных, много разных источников.Azure Storage Queue - долгое время для обработки

Клиент отправляет сообщения в очередь хранения лазурных изображений. Существуют рабочие роли, которые обрабатывают сообщения и генерируют отчеты.

Если я хочу увеличить это, допустим, у меня 10 рабочих ролей, которые будут обрабатывать сообщения из очереди и генерировать отчеты. Тогда я буду добавлять сообщения в очередь, как это:

  • сообщение 1: отчеты процесса от 1 - 5
  • сообщение 2: отчеты процесса от 6 - 11 ........
  • сообщение 10: отчеты о процессах от 50 до 55 (может быть неточным)

Если моя рабочая роль 1 примет первое сообщение и поместит блокировку, но процесс займет 5 минут, блокировка будет истечет, и сообщение будет снова видимым в очереди, так что рабочая роль 2 возьмет его и начнет процедуру ssing it ... и т. д.

Как я могу избежать того, что потребление сообщения очереди выполняется только один раз, имея в виду, что задача длинная?

ответ

1

Прежде всего: использование очередей Azure Storage должно быть подготовлено для всех ваших операций: idempotent: Если ваш элемент очереди обрабатывается несколько раз, тот же результат должен происходить каждый раз. Причина, по которой я это делаю: просто невозможно гарантировать, что вы обработаете сообщение один раз (если вы не проверите свойство DequeueCount сообщения и не прекратите обработку соответственно) из-за непредвиденных событий, таких как сбой/перезагрузка экземпляра вашей роли или ваш код обработки элементов очереди делает что-то неожиданное, как бросание исключения.

Далее: тайм-аут невидимости сообщения в очереди может быть программно расширен. Это можно сделать через очередь api или через один из языков sdk. В C# (что-то вроде этого - я не проверял это), расширяя дополнительную минуту:

queueMessage.UpdateMessage(message, 
    TimeSpan.FromSeconds(60), 
    MessageUpdateFields.Visibility); 

Вы также можете изменить сообщение по пути (возможно, как намек на свой код, чтобы узнать, какие из 5 отчетов было выполнено. Это должно помочь вашей конкретной проблеме: в случае, когда сообщение будет переработано, вам не нужно обрабатывать все пять отчетов, если сообщение было изменено, чтобы сказать что-то вроде «process reports from 3-5»). Примечание: Вы можете комбинировать MessageUpdateFields флагов через |:

queueMessage.UpdateMessage(message, 
    TimeSpan.FromSeconds(0), 
    MessageUpdateFields.Content); 

Наконец: Если вы обеспокоены продолжительностями времени, чтобы обработать партию отчетов, возможно, переосмыслить, почему вы обрабатываете пять отчетов в каждом сообщении , против одного отчета за сообщение. Вы всегда можете читать сообщения в очереди пакетами. Это становится немного субъективным, так как на самом деле нет правильного или неправильного способа сделать это, но вам просто нужно подумать.

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