跳到主要内容
版本:3.18.0

保护 WebSocket 流量

WebSocket 通过单个 TCP 连接提供持久的双向通信。初始连接建立后,客户端和服务器可以相互交换消息,无需为每次交互都创建新的 HTTP 请求。这使 WebSocket 适用于实时数据流、聊天、协作应用、多人游戏以及其他需要低延迟更新的工作负载。

每个 WebSocket 连接都从 HTTP 升级请求开始。网关必须在握手期间、连接成为持久通信通道之前完成身份认证决策。APISIX 可以将身份认证插件应用于升级请求,并在允许协议切换前拒绝未授权的客户端。

本指南会配置 key-auth 插件,并使用能在握手中添加凭证请求头的命令行客户端 websocat,验证被拒绝和已认证的连接。浏览器 WebSocket API 不允许应用设置任意请求头,因此浏览器应用应使用符合其客户端架构的身份认证方法和凭证传输方式。如果其他 APISIX 身份认证插件更适合该客户端和应用,同一握手也可以使用这些插件。

前置条件​

  • 安装 Docker。
  • 安装 cURL,以通过 Admin API 配置 APISIX。
  • 安装 websocat,以建立 WebSocket 连接。
  • 按照入门教程在 Docker 中启动 APISIX 实例。

启动 WebSocket 上游​

将 GATEWAY_CONTAINER 设置为正在运行的 APISIX 容器。创建专用网络,并将网关连接到该网络:

export GATEWAY_CONTAINER=replace-with-apisix-container-name

docker network create gateway-websocket-net
docker network connect gateway-websocket-net "$GATEWAY_CONTAINER"

在共享网络上启动已固定版本的 WebSocket 示例服务器:

docker run -d \
--name websocket-server \
--network gateway-websocket-net \
jmalloc/echo-server:v0.3.7

该服务器公开了 /.ws 端点,并会回显收到的每条消息。

创建路由​

创建一条启用 WebSocket 代理并要求 key-auth 凭证的路由:

curl "http://127.0.0.1:9180/apisix/admin/routes/websocket-auth" -X PUT \
-d '{
"uri": "/.ws",
"enable_websocket": true,
"plugins": {
"key-auth": {}
},
"upstream": {
"type": "roundrobin",
"nodes": {
"websocket-server:8080": 1
}
}
}'

创建消费者​

创建名为 john 的消费者,并为其配置 key-auth 凭证:

创建消费者:

curl "http://127.0.0.1:9180/apisix/admin/consumers" -X PUT \
-d '{
"username": "john"
}'

创建凭证:

curl "http://127.0.0.1:9180/apisix/admin/consumers/john/credentials" -X PUT \
-d '{
"id": "john-key-auth",
"plugins": {
"key-auth": {
"key": "john-key"
}
}
}'

验证身份认证​

不提供凭证即打开路由:

websocat "ws://127.0.0.1:9080/.ws"

APISIX 应以 401 Unauthorized 拒绝握手。

使用 john 的凭证打开路由:

websocat "ws://127.0.0.1:9080/.ws" -H "apikey: john-key"

发送 hello。服务器应回显该消息:

Request served by <container-id>
hello
hello

升级成功且消息被回显,证明 APISIX 已对握手完成身份认证,并能够双向代理流量。

后续步骤​

你已配置 APISIX 对 WebSocket 升级请求进行身份认证。如需控制并发连接数,请参阅限制 WebSocket 连接速率。