如何将 Azure SignalR 服务与 Azure API 管理配合使用
Azure API 管理服务为所有环境中的 API 提供了一个混合的多云管理平台。 本文介绍如何使用 Azure API 管理和 Azure SignalR 服务向应用程序添加实时功能。
重要
本文中出现的原始连接字符串仅用于演示目的。
连接字符串包括应用程序访问 Azure SignalR 服务所需的授权信息。 连接字符串中的访问密钥类似于服务的根密码。 在生产环境中,请始终保护访问密钥。 使用 Azure 密钥保管库安全地管理和轮换密钥,使用 Microsoft Entra ID 保护连接字符串,并使用 Microsoft Entra ID 授权访问。
避免将访问密钥分发给其他用户、对其进行硬编码或将其以纯文本形式保存在其他人可以访问的任何位置。 如果你认为访问密钥可能已泄露,请轮换密钥。
创建资源
按照快速入门:使用 ARM 模板部署 Azure SignalR 进行操作,并创建 SignalR 服务实例 ASRS1
按照快速入门:使用 ARM 模板部署 Azure API 管理进行操作,并创建 API 管理实例 APIM1
配置 API
限制
SignalR 客户端有两种类型的请求:
- 协商请求:发送到
<APIM-URL>/client/negotiate/
的 HTTPPOST
请求 - 连接请求:发送到
<APIM-URL>/client/
的请求,可能是WebSocket
、ServerSentEvent
或LongPolling
,具体取决于 SignalR 客户端的传输类型
连接请求的类型根据 SignalR 客户端的传输类型而异。 目前,API 管理尚不支持为同一后缀使用不同类型的 API。 由于这种限制,在使用 API 管理时,SignalR 客户端不支持从 WebSocket
传输类型回退到其他传输类型。 支持从 ServerSentEvent
回退到 LongPolling
。 以下部分介绍不同传输类型的详细配置。
当客户端通过 WebSocket
传输进行连接时配置 API
本部分介绍当 SignalR 客户端通过 WebSocket
传输进行连接时配置 API 管理的步骤。 当 SignalR 客户端通过 WebSocket
传输进行连接时,涉及到三种类型的请求:
- 用于协商的 OPTIONS 预检 HTTP 请求
- 用于协商的 POST HTTP 请求
- 用于连接的 WebSocket 请求
让我们从门户配置 API 管理。
- 在门户中转到 API 管理实例 APIM1 的“API”选项卡,选择“添加 API”,然后选择“HTTP”并使用以下参数创建 API:
- 显示名称:
SignalR negotiate
- Web 服务 URL:
https://<your-signalr-service-url>/client/negotiate/
- API URL 后缀:
client/negotiate/
- 显示名称:
- 选择创建的
SignalR negotiate
API,然后使用以下设置保存:- 在“设计”选项卡中
- 选择“添加操作”,然后使用以下参数保存:
- 显示名称:
negotiate preflight
- URL:
OPTIONS
/
- 显示名称:
- 选择“添加操作”,然后使用以下参数保存:
- 显示名称:
negotiate
- URL:
POST
/
- 显示名称:
- 选择“添加操作”,然后使用以下参数保存:
- 切换到“设置”选项卡,并取消选中“需要订阅”以进行快速演示
- 在“设计”选项卡中
- 选择“添加 API”,然后选择“WebSocket”并使用以下参数创建 API:
- 显示名称:
SignalR connect
- WebSocket URL:
wss://<your-signalr-service-url>/client/
- API URL 后缀:
client/
- 显示名称:
- 选择创建的
SignalR connect
API,然后使用以下设置保存:- 切换到“设置”选项卡,并取消选中“需要订阅”以进行快速演示
现在,API 管理已成功配置为支持具有 WebSocket
传输的 SignalR 客户端。
当客户端通过 ServerSentEvents
或 LongPolling
传输进行连接时配置 API
本部分介绍当 SignalR 客户端通过 ServerSentEvents
或 LongPolling
传输类型进行连接时配置 API 管理的步骤。 当 SignalR 客户端通过 ServerSentEvents
或 LongPolling
传输进行连接时,涉及到五种类型的请求:
- 用于协商的 OPTIONS 预检 HTTP 请求
- 用于协商的 POST HTTP 请求
- 用于连接的 OPTIONS 预检 HTTP 请求
- 用于连接的 POST HTTP 请求
- 用于连接的 GET HTTP 请求
现在让我们从门户配置 API 管理。
- 在门户中转到 API 管理实例 APIM1 的“API”选项卡,选择“添加 API”,然后选择“HTTP”并使用以下参数创建 API:
- 显示名称:
SignalR
- Web 服务 URL:
https://<your-signalr-service-url>/client/
- API URL 后缀:
client/
- 显示名称:
- 选择创建的
SignalR
API,然后使用以下设置保存:- 在“设计”选项卡中
- 选择“添加操作”,然后使用以下参数保存:
- 显示名称:
negotiate preflight
- URL:
OPTIONS
/negotiate
- 显示名称:
- 选择“添加操作”,然后使用以下参数保存:
- 显示名称:
negotiate
- URL:
POST
/negotiate
- 显示名称:
- 选择“添加操作”,然后使用以下参数保存:
- 显示名称:
connect preflight
- URL:
OPTIONS
/
- 显示名称:
- 选择“添加操作”,然后使用以下参数保存:
- 显示名称:
connect
- URL:
POST
/
- 显示名称:
- 选择“添加操作”,然后使用以下参数保存:
- 显示名称:
connect get
- URL:
GET
/
- 显示名称:
- 选择新添加的“connect get”操作,然后编辑后端策略以禁用
ServerSentEvents
的缓冲,请查看此处了解更多详细信息。<backend> <forward-request buffer-response="false" /> </backend>
- 选择“添加操作”,然后使用以下参数保存:
- 切换到“设置”选项卡,并取消选中“需要订阅”以进行快速演示
- 在“设计”选项卡中
现在,API 管理已成功配置为支持具有 ServerSentEvents
或 LongPolling
传输的 SignalR 客户端。
运行聊天
现在,流量可以通过 API 管理到达 SignalR 服务。 让我们将此聊天应用程序用作示例。 让我们一开始在本地运行它。
本文中出现的原始连接字符串仅用于演示目的。 在生产环境中,请始终保护访问密钥。 使用 Azure Key Vault 安全地管理和轮换密钥,使用 Microsoft Entra ID 保护连接字符串,并使用 Microsoft Entra ID 授权访问。
首先,让我们获取 ASRS1 的连接字符串
- 在 ASRS1 的“连接字符串”选项卡上
- 客户端终结点:使用 APIM1 的“网关 URL”输入 URL,例如
https://apim1.azure-api.cn
。 它是一个连接字符串生成器(使用反向代理时)。当你下次返回到此选项卡时,该值不会保留。输入值后,连接字符串会追加一个ClientEndpoint
部分。 - 复制连接字符串
- 客户端终结点:使用 APIM1 的“网关 URL”输入 URL,例如
- 在 ASRS1 的“连接字符串”选项卡上
克隆 GitHub 存储库 https://github.com/aspnet/AzureSignalR-samples
转到 samples/Chatroom 文件夹:
设置复制的连接字符串并在本地运行应用程序,可以看到 ConnectionString 中有一个
ClientEndpoint
部分。cd samples/Chatroom dotnet restore dotnet user-secrets set Azure:SignalR:ConnectionString "<copied-connection-string-with-client-endpoint>" dotnet run
配置客户端的传输类型
打开
wwwroot
文件夹下的index.html
,找到创建connection
时的代码,更新此代码以指定传输类型。例如,若要指定连接使用 server-sent-events 或长轮询,请将代码更新为:
const connection = new signalR.HubConnectionBuilder() .withUrl( "/chat", signalR.HttpTransportType.ServerSentEvents | signalR.HttpTransportType.LongPolling ) .build();
若要指定连接使用 WebSocket,请将代码更新为:
const connection = new signalR.HubConnectionBuilder() .withUrl("/chat", signalR.HttpTransportType.WebSockets) .build();
从浏览器打开 http://localhost:5000 并使用 F12 查看网络跟踪,可以看到连接是通过 APIM1 建立的
后续步骤
现在,你已使用 Azure SignalR 成功将实时功能添加到 API 管理。 详细了解 SignalR 服务。