Примечание.
Для доступа к этой странице требуется авторизация. Вы можете попробовать войти или изменить каталоги.
Для доступа к этой странице требуется авторизация. Вы можете попробовать изменить каталоги.
Предупреждение
Эта документация не подходит для последней версии SignalR. Взгляните на ASP.NET Core SignalR.
Версии программного обеспечения, используемые в этом разделе
- Visual Studio 2013
- .NET 4.5
- SignalR версии 2
Предыдущие версии этого раздела
Сведения о более ранних версиях SignalR см. в разделе SignalR более ранних версий.
Вопросы и комментарии
Оставьте отзыв о том, как вам понравилось это руководство и что, по вашему мнению, мы можем улучшить в комментариях в нижней части страницы. Если у вас есть вопросы, которые не связаны напрямую с руководством, их можно опубликовать на форуме ASP.NET SignalR или StackOverflow.com.
Как правило, существует два способа масштабирования веб-приложения: вертикальное масштабирование и горизонтальное масштабирование.
- Увеличение масштаба означает использование большего сервера (или более крупной виртуальной машины) с большим объемом ОЗУ, ЦП и т. д.
- Горизонтальное масштабирование означает добавление дополнительных серверов для обработки нагрузки.
Проблема с увеличением масштаба заключается в том, что вы быстро достигли предела размера компьютера. Помимо этого, необходимо масштабировать. Однако при горизонтальном масштабировании клиенты могут направляться на разные серверы. Клиент, подключенный к одному серверу, не будет получать сообщения, отправленные с другого сервера.
Одним из решений является пересылка сообщений между серверами с помощью компонента, называемого шинопроводом. При включенной задней панели каждый экземпляр приложения отправляет сообщения в заднюю панель, а задняя панель перенаправляет их другим экземплярам приложения. (В электронике коммутационная плата — это группа параллельных соединителей. По аналогии, коммутационная плата SignalR подключает несколько серверов.)
В настоящее время SignalR предоставляет три топологии:
- Azure Service Bus. Служебная шина — это инфраструктура обмена сообщениями, которая позволяет компонентам отправлять сообщения в свободно связанном виде.
- Redis. Redis — это хранилище ключей-значений в памяти. Redis поддерживает шаблон публикации и подписки (pub/sub) для отправки сообщений.
- SQL Server. Подложка SQL Server записывает сообщения в таблицы SQL. Backplane использует Service Broker для эффективного обмена сообщениями. Однако он также работает, если компонент Service Broker не включен.
При развертывании приложения в Azure рекомендуется использовать серверную планку Redis с помощью кэша Redis Azure. Если вы развертываете в собственной ферме серверов, рассмотрите серверные планки SQL Server или Redis.
В следующих темах содержатся пошаговые инструкции для каждой магистральной платы:
- Масштабирование SignalR с помощью Azure Service Bus
- Масштабирование SignalR с Redis
- Масштабирование SignalR с помощью SQL Server
Implementation
В SignalR каждое сообщение отправляется через шину сообщений. Шина сообщений реализует интерфейс IMessageBus, который предоставляет абстракцию публикации и подписки. Коммутационные платы работают путем замены IMessageBus по умолчанию шиной, предназначенной для этой коммутационной платы. Например, шина сообщений для Redis — RedisMessageBus, и она использует механизм pub/sub Redis для отправки и получения сообщений.
Каждый экземпляр сервера подключается к магистрали через шину. Когда сообщение отправляется, оно попадает в магистраль, которая пересылает его на каждый сервер. После получения сервером сообщения от бэкплейна, оно помещается в локальный кэш. Затем сервер отправляет сообщения клиентам из локального кэша.
Для каждого подключения клиента прогресс в чтении потока сообщений отслеживается с помощью курсора. (Курсор представляет позицию в потоке сообщений.) Если клиент отключается, а затем повторно подключается, он запрашивает шины все сообщения, поступающие после значения курсора клиента. То же самое происходит, когда подключение использует длинный опрос. После завершения длительного запроса опроса клиент открывает новое подключение и запрашивает сообщения, поступающие после курсора.
Механизм курсора работает, даже если клиент направляется на другой сервер при повторном подключении. Коммутационная матрица знает обо всех серверах, и неважно, к какому серверу подключается клиент.
Ограничения
Используя бекплейн, максимальная пропускная способность ниже, чем при подключении клиентов непосредственно к одному серверному узлу. Это связано с тем, что серверная планка пересылает каждое сообщение на каждый узел, поэтому обратная планка может стать узким местом. Является ли данное ограничение проблемой, зависит от приложения. Например, ниже приведены некоторые типичные сценарии SignalR:
- Широковещательная трансляция сервера (например, биржевой тикер): дальние шины работают хорошо для этого сценария, так как сервер управляет скоростью отправки сообщений.
- Клиент—клиент (например, чат): в этом сценарии серверная планка может быть узким местом, если число сообщений масштабируется с числом клиентов; То есть, если скорость сообщений пропорционально увеличивается по мере присоединения клиентов.
- Высокочастотный режим реального времени (например, игры в реальном времени): для этого сценария не рекомендуется использовать бекплейн.
Включение трассировки для горизонтального масштабирования SignalR
Чтобы включить трассировку для бэкплэйнов, добавьте следующие разделы в файл web.config под корневым элементом configuration :
<configuration>
<system.diagnostics>
<sources>
<source name="SignalR.SqlMessageBus">
<listeners>
<add name="SignalR-Bus" />
</listeners>
</source>
<source name="SignalR.ServiceBusMessageBus">
<listeners>
<add name="SignalR-Bus" />
</listeners>
</source>
<source name="SignalR.ScaleoutMessageBus">
<listeners>
<add name="SignalR-Bus" />
</listeners>
</source>
</sources>
<switches>
<add name="SignalRSwitch" value="Verbose" />
<!-- Off, Critical, Error, Warning, Information, Verbose -->
</switches>
<sharedListeners>
<add name="SignalR-Bus"
type="System.Diagnostics.TextWriterTraceListener"
initializeData="bus.log.txt" />
</sharedListeners>
<trace autoflush="true" />
</system.diagnostics>
. . .
</configuration>