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

Аннотация

Привет, я размышлял, можно ли потерять сообщение с SignalR. Предположим, клиент отключается, но в конечном итоге снова подключается за короткое время, например 3 секунды. Получит ли клиент все сообщения, которые были отправлены ему, пока он был отключен?

например, давайте рассмотрим LongPolling транспорт. Насколько мне известно, long polling-это простой http-запрос, который выдается клиентом заранее, чтобы дождаться сервера событие.

как только происходит событие сервера, данные публикуются по http-запросу, что приводит к закрытию соединения по выданному http-запросу. После этого клиент выдает новый http-запрос, который снова повторяет весь цикл.

проблема

предположим, что на сервере произошло два события, сначала A затем B (почти мгновенно). Клиент получает сообщение A что приводит к закрытию http-соединения. Теперь, чтобы получить сообщение B клиент должен выдать второй HTTP запрос.

вопрос

если B событие произошло, когда клиент был отключен от сервера и пытается переподключиться.

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

вопрос относится не только к длинному опросу, но и к общей ситуации с повторным подключением клиента.

С. П. Я использую концентраторы SignalR на сторона сервера.


редактировать:

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

1 ответов


ответ на этот вопрос лежит в методе EnqueueOperation здесь...

https://github.com/SignalR/SignalR/blob/master/src/Microsoft.AspNet.SignalR.Core/Transports/TransportDisconnectBase.cs

protected virtual internal Task EnqueueOperation(Func<object, Task> writeAsync, object state)
{
    if (!IsAlive)
    {
        return TaskAsyncHelper.Empty;
    }

    // Only enqueue new writes if the connection is alive
    Task writeTask = WriteQueue.Enqueue(writeAsync, state);
    _lastWriteTask = writeTask;

    return writeTask;
}

когда сервер отправляет сообщение клиенту, он вызывает этот метод. В приведенном выше примере сервер запросит 2 сообщения для отправки, затем клиент повторно подключится после получения первого, затем будет отправлено второе сообщение отправленный.

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

надеюсь, что это помогает