Устойчивость и аварийное восстановление Службы Azure SignalR

Устойчивость и аварийное восстановление — это одно из основных требований практически ко всем веб-системам. Служба Azure SignalR уже предоставляет 99,9 % доступности, однако она по-прежнему является региональной службой. При возникновении сбоя на уровне региона экземпляр службы не выполняет отработку отказа в другой регион, так как он всегда работает в одном регионе.

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

  • Включение георепликации (простой способ). Эта функция автоматически обрабатывает региональную отработку отказа. При включении существует только один экземпляр Azure SignalR, и изменения кода не отображаются. Дополнительные сведения см. в реплика.
  • Использование нескольких конечных точек в пакете SDK службы. Наш пакет SDK службы поддерживает несколько экземпляров службы SignalR и автоматически переключается на другие экземпляры, если некоторые из них недоступны. С помощью этой функции вы можете восстановиться при аварии, но вам нужно настроить правильную системную топологию самостоятельно. Вы узнаете, как это сделать в этом документе.

Отказоустойчивая архитектура для Службы Azure SignalR

Чтобы обеспечить устойчивость между регионами для службы SignalR, необходимо настроить несколько экземпляров служб в разных регионах. В таком случае, если один из регионов не работает, другие регионы можно использовать для резервного копирования. Когда серверы приложений подключаются к нескольким экземплярам служб, существуют две роли, первичные и вторичные. Основной — это экземпляр, ответственный за получение сетевого трафика, а вторичный — резервный экземпляр, который является полностью функциональным. В нашей реализации пакета SDK согласование возвращает только основные конечные точки, поэтому клиенты подключаются только к основным конечным точкам в обычных случаях. Но при отключении основного экземпляра согласование возвращает вторичные конечные точки, чтобы клиент по-прежнему может выполнять подключения. Первичный экземпляр и сервер приложений связаны через обычные соединения с сервером, а вторичный экземпляр и сервер приложений — через специальное соединение, называемое слабым. Одна из отличительных характеристик слабого подключения заключается в том, что не удается принять маршрутизацию подключений клиента из-за расположения вторичного экземпляра в другом регионе. Маршрутизация клиента в другой регион не является оптимальным выбором (увеличивает задержку).

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

Так как все серверы приложений и экземпляры Службы SignalR взаимосвязаны, при использовании этой топологии сообщение от одного сервера по-прежнему может доставляться всем клиентам. Но при подключении клиента он направляется на сервер приложений в том же регионе, чтобы обеспечить оптимальную задержку сети.

На следующей схеме показана такая топология:

Diagram shows two regions each with an app server and a SignalR service, where each server is associated with the SignalR service in its region as primary and with the service in the other region as secondary.

Настройка нескольких экземпляров службы SignalR

На серверах приложений и в решении "Функции Azure" поддерживаются несколько экземпляров службы SignalR.

Если вы используете службу SignalR и серверы приложений/решение "Функции Azure", созданные в каждом регионе, то их можно настроить для подключения ко всем экземплярам службы SignalR.

Настройка на серверах приложений

Это можно сделать двумя способами:

С помощью файла конфигурации.

Возможно, вы уже знаете, как задать строку подключения службы SignalR через переменные среды, параметры приложения, web.cofig в записи файла конфигурации с именем Azure:SignalR:ConnectionString. Если у вас есть несколько конечных точек, их можно задать в нескольких записях в файле конфигурации в следующем формате:

Azure:SignalR:ConnectionString:<name>:<role>

В Подключение ionString <name> — это имя конечной точки и <role> ее роль (первичная или вторичная). Имя является необязательным, но полезно, если вы хотите дополнительно настроить поведение маршрутизации между несколькими конечными точками.

С помощью кода.

Если вы предпочитаете хранить строки подключения в другом расположении, можно прочитать их с помощью кода и использовать полученные данные в качестве параметров при вызове AddAzureSignalR() (в ASP.NET Core) или MapAzureSignalR() (в ASP.NET).

Ниже приведен пример кода.

ASP.NET Core:

services.AddSignalR()
        .AddAzureSignalR(options => options.Endpoints = new ServiceEndpoint[]
        {
            new ServiceEndpoint("<connection_string1>", EndpointType.Primary, "region1"),
            new ServiceEndpoint("<connection_string2>", EndpointType.Secondary, "region2"),
        });

ASP.NET:

app.MapAzureSignalR(GetType().FullName, hub,  options => options.Endpoints = new ServiceEndpoint[]
    {
        new ServiceEndpoint("<connection_string1>", EndpointType.Primary, "region1"),
        new ServiceEndpoint("<connection_string2>", EndpointType.Secondary, "region2"),
    };

Можно настроить несколько первичных или вторичных экземпляров. Если существует несколько первичных и/или вторичных экземпляров, согласование возвращает конечную точку в следующем порядке:

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

Настройка в решении "Функций Azure"

См. статью.

Последовательность отработки отказа и рекомендации по ней

Теперь топология вашей системы настроена правильно. При каждом отключении одного экземпляра службы SignalR трафик в сети направляется в другие экземпляры. Вот что происходит, когда основной экземпляр отключен (и восстанавливается через некоторое время):

  1. Основной экземпляр службы находится вниз, все подключения к серверу в этом экземпляре отпадают.
  2. Все серверы, подключенные к этому экземпляру, помечают его как автономный, и переговоры перестают возвращать эту конечную точку и начинают возвращать вторичную конечную точку.
  3. Все клиентские подключения в этом экземпляре также закрыты, клиенты затем повторно подключаются. Так как серверы приложений теперь возвращают вторичную конечную точку, клиенты подключаются к вторичному экземпляру.
  4. Теперь вторичный экземпляр принимает весь онлайн-трафик. Все сообщения от сервера к клиентам по-прежнему доставляются, так как вторичный сервер подключен ко всем серверам приложений. Сообщения от клиента к серверу направляются только на сервер приложений в этом же регионе.
  5. После восстановления первичного экземпляра и его повторного подключения сервер приложений восстанавливает подключения к экземпляру и помечает его как подключенный. Согласование теперь возвращает основную конечную точку снова, чтобы новые клиенты были подключены к первичной. Но существующие клиенты не удаляются и по-прежнему направляются на вторичный, пока они не отключаются.

На схемах ниже показано, как в Службе Azure SignalR осуществляется аварийное переключение:

Рис.1 перед отработой отказа Before Failover

Рис.2 после отработки отказа After Failover

Рис.3 Короткое время после первичного восстановления Short time after primary recovers

Обычно онлайн-трафик обрабатывает только основной сервер приложений и первичная Служба ignalR (показано синим). После отработки отказа вторичный сервер приложений и вторичная Служба Azure SignalR также активируются. После повторного подключения первичной Службы Azure SignalR новые клиенты будут подключаться к ней. При этом клиенты продолжают подключаться к вторичному экземпляру, поэтому оба экземпляра принимают трафик. После отключения всех подключенных клиентов ваша система перейдет в обычное состояние (рис. 1).

Ниже описаны два основных вида реализации архитектуры высокого уровня, доступной между регионами.

  1. Первый — пара серверов приложений и экземпляр Службы SignalR принимают весь онлайн-трафик, а другая пара используется для резервного копирования (режим "активный — пассивный", см. рис. 1).
  2. Другой — две (или более) пары серверов приложений и экземпляров Службы SignalR, каждая из которых принимает участие в обработке онлайн-трафика и служит резервной копией для других пар (режим "активный — активный", см. рис. 3).

Служба SignalR может поддерживать оба шаблона. Основное различие заключается в том, как реализованы серверы приложений. Если серверы приложений активны и пассивны, служба SignalR также активна или пассивно (так как основной сервер приложений возвращает только его основной экземпляр службы SignalR). Если серверы приложений активны и активны, служба SignalR также активна или активна (так как все серверы приложений возвращают собственные основные экземпляры SignalR, поэтому все они могут получить трафик).

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

Кроме того, из-за характера подключения SignalR (это длинное подключение), клиенты испытывают падение подключений при возникновении аварии и отработки отказа. Необходимо обрабатывать такие случаи на стороне клиента, чтобы сделать его прозрачным для конечных клиентов. Например, подключитесь повторно после закрытия подключения.

Тестирование отработки отказа

Выполните действия, чтобы активировать отработку отказа:

  1. На вкладке "Сеть" для основного ресурса на портале отключите доступ к общедоступной сети. Если ресурс включает частную сеть, используйте правила управления доступом, чтобы запретить весь трафик.
  2. Перезапустите основной ресурс.

Следующие шаги

Из этой статьи вы узнали, как настроить приложение для обеспечения устойчивости службы SignalR. Дополнительные сведения о подключении "сервер — клиент" и маршрутизации подключений Службы Azure SignalR см. в этой статье с описанием внутренних компонентов Службы Azure SignalR.

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

Дополнительные сведения о настройке функций Azure с несколькими экземплярами службы SignalR см. в статье Поддержка нескольких экземпляров службы Azure SignalR в решении "Функции Azure".