远程 Playwright 部署¶
调用侧始终使用同一 Playwright Capability;本地、WS 与 CDP 的差异只存在于Provider 配置与资源 transport。
生产部署首选
首选在独立 Docker 容器中运行版本匹配的 Playwright WS 服务,再由 Bot 容器或宿主机通过私有容器网络连接。这样浏览器二进制、系统依赖和进程生命周期不会污染 Bot 宿主机。直接在 Bot 宿主机启动浏览器是第二选项,主要用于本地开发、单机环境或无法增加独立服务的部署。
Docker 拓扑¶
推荐拓扑包含两个职责单一的服务:
| 服务 | 安装内容 | 网络职责 |
|---|---|---|
| Bot | nonebot-plugin-htmlrender[playwright],不安装本地浏览器 |
作为 Playwright client 主动连接 WS endpoint |
| Playwright | 与 Bot lockfile 版本匹配的浏览器、Playwright server 与系统依赖 | 只在私有容器网络暴露 WS 端口 |
Playwright 官方镜像包含浏览器和系统依赖,但不包含项目的 Python package。构建服务镜像时必须把镜像 tag 和 server package 固定到 Bot lockfile 解析出的同一 Playwright 版本;不要使用 latest。除非外部 client 必须访问,否则只使用 Compose expose,不要把 WS 端口发布到宿主机或公网。官方镜像内容与版本要求见 Playwright Docker 说明。
连接远程浏览器¶
connect_ws.endpoint 与 connect_cdp.endpoint 互斥。页面导航和截图调用见操作浏览器页面。
WS 版本门禁与启动探测¶
WS 模式会在建立 Playwright 协议连接前执行 client/server 版本门禁。门禁优先从 endpoint 的 playwright_version、pw_version、version 参数或路径提取版本;无法取得时,再以有界 HTTP 请求探测同源的 /json/version 与 /。
当前门禁是风险分级,不是版本强等于:
| client/server 差异 | 行为 |
|---|---|
| major 不同,或 minor 相差至少 2 | BLOCK,拒绝连接 |
| minor 相差 1 | WARNING,记录警告后继续 |
| minor 相同、patch 相差超过 10 | WARNING,记录警告后继续 |
| 其余可识别版本 | SAFE,继续连接 |
| 无法识别远端版本 | 记录警告并继续;版本门禁 fail-open |
门禁通过后仍需由 BrowserType.connect() 完成真实协议握手。配置 startup: probe 还会在启动期取得一个 Browser lease 并创建 Page,可以提前暴露连接成功但实际浏览器不可用的问题。三者共同提供早期诊断,但软门禁不能证明任意版本组合兼容,也不能替代部署时的精确锁定。
CDP 模式不执行 Playwright client/server 版本门禁;它只校验 endpoint、限制 engine: chromium,再通过实际 CDP 连接与 startup: probe 验证可用性。
因此 Docker WS 服务仍应把 server 镜像 tag、server package 与 Bot lockfile 解析出的 Playwright client 固定到同一版本。版本门禁是误配置保护,不是允许使用浮动 tag 或放宽版本约束的兼容性承诺。
本地资源 transport¶
| 策略 | 适用场景 | 约束 |
|---|---|---|
memory |
默认远程部署 | asset 只活到单次操作结束,无共享磁盘要求 |
passthrough |
Bot 与浏览器有相同挂载点 | 两端路径必须完全一致 |
filehost |
浏览器必须通过 HTTP 拉取资源 | 需要路由、请求头保护与 CORS 响应 |
error |
禁止本地资源 | 发现本地引用立即失败 |
memory 读取受授权资源、按内容去重,并由 Page route 返回 bytes、媒体类型、cache
header 与 CORS 响应。passthrough 不上传文件;容器路径不一致时必然失败。
memory asset 只存活于当前 render lease,不是跨调用 cache。filehost 的 content-addressed mapping、TTL、预热、hosted store LRU 与 lease 钉住语义见缓存组件、失效与调优。
Filehost¶
render:
provider: playwright
provider_config:
remote_local_resource_policy: filehost
resources:
local_access:
allowed_paths:
- /app/assets
filehost:
public_base_url: https://bot.example/
cache_ttl_seconds: 300
请求头守卫必须保持开启。反向代理向 Bot 透传守卫请求头,并保留资源响应的 CORS header;CORS 不承担授权。完整容量与访问策略见资源、缓存与访问策略。
健康检查与部署检查表¶
startup: probe 在 NoneBot 启动期验证连接并创建 Page;运行中可调用await get_default_application().probe()。部署还需确认:
- Provider extra 与远程服务 Playwright 精确锁定到同一版本,不以软版本门禁代替依赖管理;
- endpoint 不向不可信网络开放,CDP 服务具备网络隔离和认证;
- local access 白名单最小化,默认使用
memory; - 导航目标遵守 SSRF 策略;
- shutdown 能在有界时间内关闭连接并唤醒等待者。