本文介绍如何使用 Socket.IO 无服务器与 Azure Functions 集成。
| Action | 绑定类型 |
|---|---|
| 获取客户端协商结果,包括 URL 和访问令牌 | 输入绑定 |
| 由来自服务的消息触发 | 触发器绑定 |
| 调用服务以发送消息或管理客户端 | 输出绑定 |
源代码 | 包 | API 参考文档 | 产品文档 | 示例
重要
Azure 函数绑定只能在无服务器模式下与用于 Socket.IO 的 Web PubSub 集成。
身份验证和连接字符串
若要让扩展与 Web PubSub for Socket.IO 配合使用,您需要提供访问密钥或基于身份的配置,以便进行身份验证。
基于访问密钥的配置
| 配置名称 | Description |
|---|---|
| WebPubSubForSocketIOConnectionString | 必填。 服务中基于密钥的连接字符串 |
在 Azure 门户的 Web PubSub 中的“密钥”边栏选项卡下,您可以找到用于 Socket.IO 的连接字符串。
对于本地开发,请使用 local.settings.json 该文件来存储连接字符串。 将 WebPubSubForSocketIOConnectionString 设置为从上一步复制的连接字符串。
{
"Values": {
"AzureWebJobsStorage": "UseDevelopmentStorage=true",
`WebPubSubForSocketIOConnectionString`: "Endpoint=https://<webpubsub-name>.webpubsub.azure.com;AccessKey=<access-key>;Version=1.0;"
}
}
部署后,使用 应用程序设置 设置连接字符串。
基于标识的配置
| 配置名称 | Description |
|---|---|
| WebPubSubForSocketIOConnectionString__endpoint | 必填。 服务的终结点。 例如: https://mysocketio.webpubsub.azure.com |
| WebPubSubForSocketIOConnectionString__credential | 定义如何为连接获取令牌。 如果部署的 Azure 函数打算使用托管标识身份验证,则此设置应设置为 managedidentity。 仅当托管标识在托管环境中可用时,此值才有效。 |
| WebPubSubForSocketIOConnectionString__clientId | 当 credential 设置为“managedidentity”时,此属性可以设为指定在获取令牌时要使用的用户分配的标识。 该属性接受与分配给应用程序的用户分配的标识对应的客户端 ID。 如果未指定,则使用系统分配的标识。 |
函数绑定遵循基于标识的配置的通用属性。 有关更多未提及的属性,请参阅 基于标识的连接的常用 属性。
对于本地开发,请使用 local.settings.json 该文件来存储连接字符串。 将 WebPubSubForSocketIOConnectionString 设置为从上一步复制的连接字符串:
{
"Values": {
"AzureWebJobsStorage": "UseDevelopmentStorage=true",
"WebPubSubForSocketIOConnectionString__endpoint": "https://<webpubsub-name>.webpubsub.azure.com",
"WebPubSubForSocketIOConnectionString__tenant": "<tenant id you're in>",
}
}
如果要使用基于标识的配置并联机运行, AzureWebJobsStorage 应指 使用标识连接到主机存储。
输入绑定
Socket.IO 输入绑定向客户端发送一个 SocketIONegotiationResult 以启动协商请求。 当 Socket.IO 客户端尝试连接到服务时,它需要知道 endpoint、path 和 access token 以进行身份验证。 让服务器生成这些数据是一种常见做法,这称为协商。
[FunctionName("SocketIONegotiate")]
public static IActionResult Negotiate(
[HttpTrigger(AuthorizationLevel.Anonymous, "get")] HttpRequest req,
[SocketIONegotiation(Hub = "hub", UserId = "userId")] SocketIONegotiationResult result)
{
return new OkObjectResult(result);
}
Attribute
输入绑定的属性为 [SocketIONegotiation].
| Attribute 属性 | Description |
|---|---|
| Hub | 客户端需要连接到的中心名称。 |
| 连接 | 包含 Socket.IO 连接字符串的应用设置的名称(默认值为 WebPubSubForSocketIOConnectionString)。 |
| UserId | 连接的用户ID。 它适用于连接中的所有套接字。 它成为生成的sub令牌的声明。 |
触发器绑定
Azure Function 使用触发器绑定以触发函数处理来自 Web PubSub for Socket.IO 的事件。
触发器绑定公开了遵循 Azure 函数终结点的特定路径。 URL 应设置为服务的 URL 模板(门户:设置 -> 事件处理程序 -> URL 模板)。 在终结点模式中,出于code=<API_KEY>原因使用 Azure Function 应用时,查询部分 是必需的。 密钥可在“Azure 门户”中找到。 找到函数应用资源,并在将函数应用部署到 Azure 后导航到 Functions ->App 密钥> -系统密钥 ->socketio_extension。 但是,在使用本地函数时不需要此密钥。
<Function_App_Endpoint>/runtime/webhooks/socketio?code=<API_KEY>
套接字连接事件触发的函数。
[FunctionName("SocketIOTriggerConnect")]
public static async Task<SocketIOEventHandlerResponse> Connect(
[SocketIOTrigger("hub", "connect")] SocketIOConnectRequest request)
{
return new SocketIOConnectResponse();
}
套接字连接事件的触发函数。
[FunctionName("SocketIOTriggerConnected")]
public static async Task Connected(
[SocketIOTrigger("hub", "connected")] SocketIOConnectedRequest request)
{
}
用于套接字断开连接事件的函数触发器。
[FunctionName("SocketIOTriggerDisconnected")]
public static async Task Disconnected(
[SocketIOTrigger("hub", "disconnected")] SocketIODisconnectedRequest request)
{
}
来自客户端的普通消息的函数触发器。
[FunctionName("SocketIOTriggerMessage")]
public static async Task NewMessage(
[SocketIOTrigger("hub", "new message")] SocketIOMessageRequest request,
[SocketIOParameter] string arg)
{
}
特性
触发器绑定的属性为 [SocketIOTrigger].
| Attribute 属性 | Description |
|---|---|
| Hub | 客户端需要连接到的中心名称。 |
| Namespace | 套接字的命名空间。 默认值:“/” |
| 事件名称 | 函数触发的事件名称。 某些事件名称是预定义的: connect 用于套接字连接事件。
connected 用于套接字连接事件。
disconnected 用于处理断开连接的套接字事件。 其他事件由用户定义,它需要匹配客户端发送的事件名称。 |
| 参数名称 | 事件的参数名称列表。 列表长度应与从客户端发送的事件一致。 该名称使用 Binding 表达式 并通过同名函数参数进行访问。 |
绑定数据
[SocketIOTrigger] 将某些变量绑定到绑定数据。 可以从 Azure Functions 绑定表达式模式了解有关它的详细信息
SocketIOAttribute
SocketIOAttribute 是一种替代方法 ParameterNames,它简化了函数定义。 例如,以下两个定义具有相同的效果:
[FunctionName("SocketIOTriggerMessage")]
public static async Task NewMessage(
[SocketIOTrigger("hub", "new message")] SocketIOMessageRequest request,
[SocketIOParameter] string arg)
{
}
[FunctionName("SocketIOTriggerMessage")]
public static async Task NewMessage(
[SocketIOTrigger("hub", "new message", ParameterNames = new[] {"arg"})] SocketIOMessageRequest request,
string arg)
{
}
请注意, ParameterNames 不能 [SocketIOParameter] 一起使用。
输入绑定的请求
输入绑定参数的数据结构因消息类型而异。
Connect
{
"namespace": "",
"socketId": "",
"claims": {
"<claim-type>": [ "<claim-value>" ]
},
"query": {
"<query-key>": [ "<query-value>" ]
},
"headers":{
"<header-name>": [ "<header-value>" ]
},
"clientCertificates":{
{
"thumbprint": "",
"content": ""
}
}
}
| 资产 | Description |
|---|---|
| 命名空间 | 套接字的命名空间。 |
| socketId | 套接字的唯一标识。 |
| 声明 | 客户端连接的 JWT 声明。 请注意,这里不是指服务请求函数时的 JWT,而是指 Engine.IO 客户端连接服务时的 JWT。 |
| 查询 | 客户端连接的查询。 请注意,查询不是发生在服务请求函数时,而是当 Engine.IO 客户端连接到服务时进行的。 |
| 标题 | 客户端连接的标头。 请注意,关键不在于服务请求函数时的标头,而在于 Engine.IO 客户端连接到服务时的标头。 |
| 客户端证书 | 如果启用了客户端证书 |
已连接
{
"namespace": "",
"socketId": "",
}
| 资产 | Description |
|---|---|
| 命名空间 | 套接字的命名空间。 |
| socketId | 套接字的唯一标识。 |
已断开连接
{
"namespace": "",
"socketId": "",
"reason": ""
}
| 资产 | Description |
|---|---|
| 命名空间 | 套接字的命名空间。 |
| socketId | 套接字的唯一标识。 |
| 原因 | 连接关闭原因说明。 |
普通事件
{
"namespace": "",
"socketId": "",
"payload": "",
"eventName": "",
"parameters": []
}
| 资产 | Description |
|---|---|
| 命名空间 | 套接字的命名空间。 |
| socketId | 套接字的唯一标识。 |
| 有效负载 | Engine.IO 协议中的消息数据负载 |
| 事件名称 | 请求的事件名称。 |
| parameters | 消息的参数列表。 |
输出绑定
输出绑定当前支持以下功能:
- 将套接字添加到会议室
- 从房间中删除套接字
- 将消息发送到套接字
- 将消息发送到房间
- 将消息发送到命名空间
- 断开连接套接字
[FunctionName("SocketIOOutput")]
public static async Task<IActionResult> SocketIOOutput(
[SocketIOTrigger("hub", "new message")] SocketIOMessageRequest request,
[SocketIO(Hub = "hub")] IAsyncCollector<SocketIOAction> collector)
{
await collector.AddAsync(SocketIOAction.CreateSendToNamespaceAction("new message", new[] { "arguments" }));
}
Attribute
输入绑定的属性为 [SocketIO].
| Attribute 属性 | Description |
|---|---|
| Hub | 客户端需要连接到的中心名称。 |
| 连接 | 包含 Socket.IO 连接字符串的应用设置的名称(默认值为 WebPubSubForSocketIOConnectionString)。 |
行动
输出绑定使用行动来执行操作。 目前,我们支持以下操作:
AddSocketToRoomAction
{
"type": "AddSocketToRoom",
"socketId": "",
"room": ""
}
RemoveSocketFromRoomAction
{
"type": "RemoveSocketFromRoom",
"socketId": "",
"room": ""
}
SendToNamespaceAction
{
"type": "SendToNamespace",
"eventName": "",
"parameters": [],
"exceptRooms": []
}
SendToRoomsAction
{
"type": "SendToRoom",
"eventName": "",
"parameters": [],
"rooms": [],
"exceptRooms": []
}
SendToSocketAction
{
"type": "SendToSocket",
"eventName": "",
"parameters": [],
"socketId": ""
}
DisconnectSocketsAction
{
"type": "DisconnectSockets",
"rooms": [],
"closeUnderlyingConnection": false
}