Связь между службами Azure Service Fabric

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

Следующее не работает (для службы Listener исключать из очереди нечего):

PublisherService:

protected override async Task RunAsync(CancellationToken cancellationToken)
{
    var myQueue = await StateManager.GetOrAddAsync<IReliableQueue<string>>("fooQueue");
    while (true)
    {
        cancellationToken.ThrowIfCancellationRequested();
        using (var tx = this.StateManager.CreateTransaction())
        {
            // Put some message in the queue
            await myQueue.EnqueueAsync(tx, "Foobar");

            await tx.CommitAsync();
        }

        await Task.Delay(TimeSpan.FromSeconds(1), cancellationToken);
    }
}

ListenerService:

protected override async Task RunAsync(CancellationToken cancellationToken)
{
    var myQueue = await StateManager.GetOrAddAsync<IReliableQueue<string>>("fooQueue");
    while (true)
    {
        cancellationToken.ThrowIfCancellationRequested();
        using (var tx = this.StateManager.CreateTransaction())
        {
            var result = await myQueue.TryDequeueAsync(tx);

            if (result.HasValue)
            {
                ServiceEventSource.Current.ServiceMessage(this.Context, "New message receieved: {0}", result.Value.ToString());
            }

            await tx.CommitAsync();
        }

        await Task.Delay(TimeSpan.FromSeconds(1), cancellationToken);
    }
}

Похоже, объем очереди ограничен одной службой. Это не похоже на ограничение, указанное в документации.

Итак, мои вопросы:

  • это на самом деле недокументированное ограничение?
  • или что-то не так в приведенном выше коде?
  • как я могу реализовать описанный выше сценарий (одна служба добавляет сообщения в очередь, другая - извлекает сообщения из той же очереди)?

Очевидно, я мог бы использовать служебную шину Azure, но не могу по нескольким причинам:

  • в моем реальном сценарии у меня будет несколько очередей (переменное число), поэтому потребуется создание очередей служебной шины по запросу (что не совсем быстрая операция)
  • добавляет зависимость к другой службе Azure (что увеличивает вероятность отказа для всей системы)
  • стоит дороже
  • более сложное развертывание
  • и Т. Д.

person ken2k    schedule 29.05.2017    source источник


Ответы (3)


ReliableQueues являются локальными для службы, да, потому что ее цель - сохранить состояние для этой конкретной службы. Это состояние реплицируется на другие экземпляры. Это как обычный System.Collections.Generic.Queue<T> в .Net.

Для недорогого решения, возможно, вы можете использовать Очереди хранилища Azure. Да, он добавляет зависимость, но имеет высокую доступность. Это компромисс, с которым можете решить только вы.

С другой стороны, мыслите нестандартно:

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

class QueuingService
{
    void AddToQueue<T>(string queuename, T input) { .. }
    void DeQueue(string queuename) { .. }
}

Это, конечно, создает зависимость, но имеет все механизмы безопасности, которые предоставляет Service Fabric, и не требует больших затрат. Но опять же, вы сами создаете очередь служебной шины / лазурного хранилища для бедных.

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

Service Fabric предлагает модель программирования с отслеживанием состояния, доступную разработчикам .NET через Reliable Collections. В частности, Service Fabric предоставляет надежный словарь и надежные классы очередей. Когда вы используете эти классы, ваше состояние (моя интерпретация: состояние службы) разделяется (для масштабируемости), реплицируется (для доступности) и передается внутри раздела (для семантики ACID).

person Peter Bons    schedule 29.05.2017
comment
Спасибо за ответ, в этом есть смысл. Я еще не уверен, какой путь я выберу (очереди хранилища Azure или удаленное общение). У каждого есть свои плюсы / минусы. Еще раз спасибо, это было очень полезно. - person ken2k; 30.05.2017
comment
Но опять же, вы сами создаете очередь служебной шины / лазурного хранилища для бедных. - это означает, что это неправильный способ использования ReliableQueue? - person AsValeO; 30.08.2017
comment
@AsValeO, что ты имеешь в виду под правильным способом. Если вы используете его для того, для чего он предназначен: хранить данные в том месте, где они используются, то есть внутри одной службы с отслеживанием состояния. Вы просто не можете превратить это во что-то еще, например, в очередь, охватывающую несколько служб. - person Peter Bons; 31.08.2017
comment
можем ли мы использовать что-то вроде очередей хранилища Azure в локальной среде? нам нужен какой-то тип решения, управляемого событиями / локально, где служба запускает сообщение, и оно будет храниться в какой-то очереди, где другая служба вытолкнет его из очереди и обработает - person Alex Gordon; 19.02.2018

Ознакомьтесь с службой очереди приоритетов, созданной для этой цели.

person Todd Abel    schedule 30.05.2017

Если вы добавляете шаблон повтора обработки ошибок ко всему вызывающему коду, вам не потребуется очередь между вызовами, см. https://docs.microsoft.com/en-us/azure/service-fabric/service-fabric-reliable-services-communication < / а>

Соответствующая часть ссылки находится здесь:

Обработчик исключений отвечает за определение действия, которое следует предпринять при возникновении исключения. Исключения подразделяются на повторяющиеся и неповторяемые. Неповторяемые исключения просто возвращаются обратно вызывающей стороне. Повторяемые исключения далее подразделяются на временные и непреходящие. Временные исключения - это те, которые можно просто повторить без повторного разрешения адреса конечной точки службы. Они будут включать временные сетевые проблемы или ответы об ошибках службы, кроме тех, которые указывают, что адрес конечной точки службы не существует. Непрерывные исключения - это те, которые требуют повторного разрешения адреса конечной точки службы. К ним относятся исключения, которые указывают на то, что конечная точка службы не может быть достигнута, что указывает на то, что служба перемещена на другой узел.

person Robert    schedule 20.09.2017