websocketd QA 测试计划全解析:以 CATEGORY-NNN 编号体系构建 WebSocket 服务器的工程质量保障
2026/9/21 1:25:30 网站建设 项目流程

websocketd QA 测试计划全解析:以 CATEGORY-NNN 编号体系构建 WebSocket 服务器的工程质量保障

【免费下载链接】websocketdTurn any program that uses STDIN/STDOUT into a WebSocket server. Like inetd, but for WebSockets.项目地址: https://gitcode.com/gh_mirrors/we/websocketd

本篇技术指南以 qa/plans/README.md 为骨架,完整剖析 websocketd 项目的质量保障(QA)测试计划体系:从测试用例的组织格式、14 类测试分类,到核心 WebSocket、进程管理、CLI 配置、HTTP 路由、安全、CGI 环境、多平台兼容、性能与边界回归等全部测试维度。读完本文,你将掌握如何像官方 QA 一样系统性地验证一个"STDIN/STDOUT 即服务"型 WebSocket 服务器,并能将这套 P0–P3 优先级、编号可追溯的用例方法论直接复用到自己的服务端项目中。

一、测试计划文档体系:总纲与用例格式

websocketd的 QA 测试计划存放在仓库的 qa/plans/ 目录下,以 README.md 作为总纲,按功能类别拆分为多个独立计划文件。每个计划文件覆盖一类功能,测试用例在各自文件内按CATEGORY-NNN格式连续编号(例如CORE-001PROC-008),保证用例 ID 全局唯一、可追踪、可回溯。

每个测试用例统一包含六个要素,这是整套计划可执行、可复现的基础:

要素说明
ID唯一标识符,如CORE-001
Title简要描述测试目标
Priority优先级:P0(关键)、P1(高)、P2(中)、P3(低)
Preconditions测试前的环境与前置准备
Steps精确到命令级别的操作步骤
Expected Result明确的预期行为
Notes补充上下文、已知问题与回归历史

值得注意的一点:Notes字段不仅记录"怎么做",还承载了大量回归历史——每条备注往往关联一个具体 commit 或 issue 号(如eee5350#159#431),这使得 QA 计划同时具备"回归测试清单"的属性:凡是历史上出过 bug 的场景,都被固化成一条用例,防止问题复发。

二、十四类测试总览:类别地图

README 以表格形式给出了完整的测试分类。下表按仓库根目录转换后的相对路径列出:

文件类别覆盖范围
01-core-websocket.mdCore WebSocket基础连接生命周期、文本/二进制消息
02-process-management.mdProcess Management子进程启动、stdio 管道、终止
03-cli-configuration.mdCLI & Configuration命令行参数、参数校验、默认值
04-http-routing.mdHTTP & Routing静态文件、CGI、开发控制台、脚本目录模式
05-security.mdSecurityOrigin 校验、TLS/SSL、环境隔离
06-environment-cgi.mdEnvironment Variables & CGIRFC 3875 合规、HTTP 头透传
07-platform-windows.mdWindows PlatformWindows 特有行为、行尾、脚本类型
08-platform-unix.mdUnix PlatformsmacOS、Linux、ARM、容器
09-protocol-compatibility.mdProtocol CompatibilityWebSocket 版本、HTTP 版本、浏览器测试
10-edge-cases-errors.mdEdge Cases & Errors畸形输入、崩溃、异常状态
11-performance-scalability.mdPerformance & Scalability并发连接、大消息、资源限制
12-dev-console.mdDeveloper Console交互式测试 UI 功能
13-examples-languages.mdLanguage Examples跨语言示例脚本测试
14-build-release.mdBuild & Release交叉编译、打包、版本管理

说明:README 的类别表列出了14-build-release.md(构建与发布),但经核实当前 qa/plans/ 目录下仅有 01–13 号计划文件,该文件尚未落地。其余 13 个文件均为可读、可执行的完整计划。

三、核心 WebSocket 功能测试(CORE)

01-core-websocket.md 共 20 条用例(CORE-001 至 CORE-020),覆盖连接生命周期与消息行为的最基础层面,其中 9 条为 P0 关键用例。这些测试几乎全部可以直接复现:启动websocketd --port=8080 cat,再用wscat -c ws://localhost:8080/连接即可。

3.1 连接生命周期

  • CORE-001 基本连接:服务端必须返回 HTTP 101 Switching Protocols,日志无错误。
  • CORE-005 客户端断开:客户端断开后,子进程(如cat)应被终止,日志记录断开事件,不留僵尸进程
  • CORE-006 服务端进程退出:脚本处理完一条消息后exit 0,服务端应主动关闭连接。
  • CORE-016 WebSocket Close Frame:客户端发送 code 1000 的关闭帧,服务端应答并干净地终止连接与子进程。
  • CORE-017 Ping/Pong:服务端响应 pong 帧且连接保持打开(由 gorilla/websocket 库处理)。

3.2 文本模式的行缓冲语义

websocketd 的核心模型是"一行消息 = 一个 WebSocket 帧":

  • CORE-010 行缓冲:客户端发送的每一行成为进程 stdin 的一行;进程 stdout 的每一行成为一帧,行分隔符为\n
  • CORE-011 换行符剥离:进程输出\n\r\n结尾的行时,尾部换行均被剥离后作为独立消息发送。

CORE-011 的 Notes 直接指向实现:trimEOL函数同时处理\n\r\n,单元测试位于 endpoint_test.go。源码佐证见 process_endpoint.go:"trimEOL cuts unixy style\nand windowsy style\r\nsuffix from the string"。

3.3 二进制模式

  • CORE-008 二进制基础--binary模式下应使用二进制帧(opcode 0x02)回显原始字节,不做任何换行处理。Notes 记录了一个经典回归:二进制帧加倍 bug(2016 年 5 月由 commiteee5350修复),验证要点是数据长度必须与输入严格一致。
  • CORE-009 大负载:1MB 二进制负载逐字节一致,无截断或损坏。
  • CORE-020 标志变体--binary--binary=true启用二进制模式;--binary=false或不加参数使用文本模式(默认)。

3.4 并发、大消息与 Unicode

  • CORE-012 多并发连接:每个连接拥有独立的子进程,消息互不串线("Connection A receives from A, B receives from B")。
  • CORE-013 快速连断:循环 100 次连接即断,服务端不得崩溃、泄漏资源或出现僵尸进程。
  • CORE-014 大文本消息:单条 1MB 文本消息完整回显。
  • CORE-015 Unicode 文本:覆盖 ASCII、拉丁扩展(cafe\u0301)、CJK(你好世界)、Emoji(🎉🚀)、混合(hello 世界 🌍)均须原样回显。Notes 提示 issue #348 曾报告中文乱码问题,可能源于某些脚本语言的缓冲或编码处理——这是"跨语言 UTF-8 保真"的重要验证锚点。

3.5 异常路径

  • CORE-018 进程崩溃:脚本exit 1后,首个连接收到 "starting" 后关闭,第二个连接仍能正常工作(重新生成新进程),退出码 1 不会拖垮 websocketd。
  • CORE-019 不存在的命令websocketd --port=8080 /nonexistent/command时服务端可启动,但连接优雅失败并返回适当错误,无 panic。

四、进程生命周期与资源管理测试(PROC)

02-process-management.md 的 22 条用例(PROC-001 至 PROC-022)把"子进程即连接"的架构模型拆解为可验证的行为契约。

4.1 每连接一进程

PROC-001 用打印 PID 的脚本验证:客户端 A、B 连接后收到的 PID必然不同——每个 WebSocket 连接都会 fork 一个新的子进程。这正是 websocketd 与常规常驻型 WebSocket 服务器的根本差异:并发能力 = 进程数,因此--maxforks这类限制器至关重要。

4.2 三路流:stdin / stdout / stderr

  • PROC-002:客户端消息以"test input\n"形式写入进程 stdin。
  • PROC-003:进程启动即输出welcomeready,客户端连接后立即收到两条独立消息。
  • PROC-004:stderr 内容只进服务端日志,绝不进 WebSocket--loglevel=debug时可在日志中看到)。
  • PROC-022--passstderr:开启后,stdout 与 stderr 均以 JSON 消息到达客户端,形如{"stream":"stdout","data":"..."}/{"stream":"stderr","data":"..."},且无论是否开启该标志,stderr 始终写入服务端日志;关闭时仅 stdout 到达客户端且不加标签(与旧版本行为一致)。关键约束--binary--passstderr互斥,同时指定会在启动时报错——这一约束在 help.go 的帮助文本中有明确记载。

4.3 优雅终止的信号升级序列(源码级验证)

PROC-005 是理解 websocketd 进程管理的核心用例:客户端断开后,子进程会收到逐级升级的终止信号。以捕获 INT/TERM 的脚本验证实际送达情况,对应实现位于 process_endpoint.go:

stdin 关闭 → 等待 100ms + closems → SIGINT → 等待 250ms + closems → SIGTERM → 等待 500ms + closems → SIGKILL → 等待 1000ms

即:先关闭 stdin 给进程优雅收尾的机会(很多程序读到 EOF 自然退出),随后依次发送 SIGINT、SIGTERM,最后以 SIGKILL 兜底;每一步之间若进程已退出则立即返回。--closems为前三个等待阶段统一追加宽限期(PROC-006、PROC-007 分别验证--closems=3000--closems=0立即击杀)。计划文件记录的期望时序为默认 100ms/250ms/500ms、带--closems时按比例延长,具体以运行二进制与源码为准。Notes 还记录了回归历史:进程挂起 bug由 commit3f89f2e(issue #159)修复。

4.4 --maxforks 并发上限

  • PROC-008--maxforks=2时第三个连接收到HTTP 429 Too Many Requests,升级被拒,前两个连接不受影响。Notes 关联 issue #366——客户端难以区分"fork 数达上限"与"服务端错误"。
  • PROC-009:客户端 A 断开后计数递减,之前被 429 拒绝的客户端 B 可再次连接成功。
  • PROC-021--maxforks=0表示无限制(仅受系统资源约束)。

默认上限并非无限:config.go 中defaultMaxForks = 1024,注释明确它是"防止失控的后备闸(runaway backstop)而非容量规划",因为每个 fork 都是完整子进程,无限(0)会让单个客户端通过狂开连接 fork 轰炸主机。

4.5 异常退出与目录模式

  • PROC-010/011/012/018:非零退出码(42)、C 程序段错误(segfault)、脚本无执行权限、进程立即退出——全部要求"连接关闭、错误入日志、websocketd 自身不崩溃、其他连接不受影响"。
  • PROC-013/014--dir脚本目录模式下,每个 URL 映射到对应脚本,不存在则 404;ws://host/echo.sh/extra/pathSCRIPT_NAME=/echo.shPATH_INFO=/extra/path(Notes 指向 handler_test.go)。
  • PROC-016 输出缓冲:这是新手最容易踩的坑——Python 脚本只写"partial..."不换行时客户端收不到任何消息,直到换行出现才收到整条"partial...complete"文本模式是行缓冲的,换行是分隔符。Notes 记录了 issues #406、#388(PHP)、#400 等大量缓冲问题:很多语言在 stdout 非终端时启用全缓冲,脚本必须主动 flush。

五、CLI 配置与参数校验测试(CLI)

03-cli-configuration.md 的 32 条用例验证命令行解析、校验与默认值。这部分与 help.go 中的完整选项清单一一对应,是理解 websocketd 配置面的最佳入口。

5.1 端口与监听地址

  • CLI-001 默认端口:不带--port时监听80(HTTP)或443(SSL)。源码佐证 config.go 的resolvePort函数。
  • CLI-002/003/004:自定义端口、端口占用(第二个实例应报清晰错误且不影响第一个)、非法端口(99999/-1/abc)均须给出明确错误并拒绝启动。
  • CLI-005/006/007/008--address支持多个(多地址同时监听)、127.0.0.1仅本机、0.0.0.0全接口、IPv6 需方括号--address=[::1]

5.2 日志级别与基础标志

  • CLI-009 日志级别(从最详细到最不详细):debug(详细内部状态)、trace(逐请求细节)、access(连接/断开事件)、info(启动与重要事件)、error(仅错误)、fatal(仅致命错误);每个级别包含其之上所有更严重级别
  • CLI-010/011/012--version(如 "websocketd 0.4.1")、--help(完整选项说明,commit169ecec修复 issue #436)、--license(BSD-2-Clause 文本)均在打印后立即退出。

5.3 参数组合校验

  • CLI-013:既无命令也无--dir时报错并显示帮助。
  • CLI-014--dir与命令同时指定报错。
  • CLI-026/030--ssl缺证书/密钥时报错(panic 曾由 commit334a9ec修复,issue #431);--ssl不指定--address时正常启动。校验逻辑见 config.go 的validateSSL
  • CLI-031--binary三种写法的行为验证。
  • CLI-029 解析边界:空格代替=、未知标志、空值等均由 Go flag 包处理。

5.4 环境透传与请求头

  • CLI-015/016/017--passenv=MY_VAR单选、逗号分隔多选(VAR1,VAR2,VAR3)、指定不存在的变量(不崩溃,仅不出现)。
  • CLI-019/020--header应用于所有响应;--header-ws仅 WebSocket 升级响应、--header-http仅普通 HTTP 响应,两者互不串扰。

5.5 同源、静态资源与 Unix Socket

  • CLI-021/022--sameorigin拒绝跨域;--origin=example.com:8080白名单精确匹配 host:port。
  • CLI-023/024/025--devconsole提供交互式测试页;--staticdir让 HTTP 请求返回静态文件而 WebSocket 仍由命令处理;--cgidir执行 CGI 脚本。
  • CLI-032 Unix Domain Socket(5 步完整生命周期验证):仅指定--unixsocket完全不启动 TCP 监听;客户端可直连 socket 路径;进程被 SIGKILL 后残留的陈旧 socket 文件会被自动清理而非报 "address already in use";可与 TCP 监听并存;第二个实例若指向仍被监听的 socket 路径则报 "socket ... is already in use by a running server" 且不得覆盖活着的 socket。对应实现见 config.go 的wantsUnixSocketOnly

六、HTTP 路由测试(HTTP)

04-http-routing.md 的 23 条用例覆盖 URL 路由的完整矩阵。

6.1 升级与普通请求

  • HTTP-001:带标准升级头的请求(Upgrade: websocketConnection: UpgradeSec-WebSocket-KeySec-WebSocket-Version: 13)返回 101。
  • HTTP-002:普通 HTTP GET不得执行脚本,返回错误或空响应。
  • HTTP-023:升级头变体(Connection: keep-alive, Upgrade、小写、混合大小写Upgrade: WebSocket)均须被接受。

6.2 静态文件

  • HTTP-003/004/005:MIME 类型正确、子目录嵌套文件可访问、缺失文件 404。
  • HTTP-006(P0 安全)路径穿越防护../../../etc/passwd、URL 编码变体(..%2F..%2F%2e%2e/)一律拦截(404 或 403),绝不越界服务文件。
  • HTTP-007/019:静态文件与 WebSocket 同端口共存、10 个 WebSocket + 100 个 HTTP 请求并发互不干扰。

6.3 CGI 与目录模式

  • HTTP-008/009/010:CGI 脚本执行、QUERY_STRING传递、子目录脚本(issue #453 曾报告 cgi-dir 子目录问题)。
  • HTTP-011/012/013--dir模式 URL 映射、不存在脚本 404、路径穿越(../../etc/passwd%2e%2e/secret.sh)无法逃逸脚本目录。
  • HTTP-014:脚本目录中的非可执行文件返回错误而非崩溃(commit11610d0在协议切换前做最终存在性检查)。

6.4 头与请求语义

  • HTTP-016/017:单条与多条自定义头。
  • HTTP-018:Host 头解析(example.com:8080与无端口)推导 SERVER_NAME/SERVER_PORT,缺失 Host 优雅处理(commit63bf0cb修复 80 端口处理)。
  • HTTP-020/021/022:HEAD 请求无 body 不崩溃;WebSocket URL 带?key=value时 QUERY_STRING 注入子进程环境;URL fragment 按规范不发送到服务端。

七、安全测试(SEC)

05-security.md 的 26 条用例把安全面切分为五个维度。

7.1 Origin 校验

  • SEC-001/002--sameorigin下同源成功、跨源(http://evil.com)被拒(403)。
  • SEC-004/005/006/007--origin白名单精确匹配 host:port(trusted.com:3000trusted.com:4000严格区分,无端口不匹配);逗号分隔多白名单。
  • SEC-008Origin: null(沙箱 iframe、file:// 页面发送)不得匹配同源——v0.2.10 修复。
  • SEC-010:默认(不加任何标志)接受任意来源,这是默认行为,生产环境需自行决策。

7.2 环境隔离(安全关键)

  • SEC-011:不指定--passenv时,父进程的SECRET_KEYDATABASE_URL等敏感变量不可见,子进程只见 CGI 标准变量。
  • SEC-012--passenv=SAFE只透传白名单项。

7.3 TLS

  • SEC-013/015/016:自签证书握手成功;证书与密钥不匹配、文件缺失均报清晰错误且不启动、不 panic。
  • SEC-014 协议版本:SSL3 不再支持(v0.2.12 移除);TLS 1.2/1.3 应可用;更旧版本取决于 Go 的 TLS 默认(Go 1.18+ 默认禁用 TLS 1.0/1.1)。

7.4 注入与 DoS 防护

  • SEC-017/018:脚本目录模式下 URL 路径中的;ls$(whoami)|cat按文件路径处理,无 shell 注入;query string 仅作为 QUERY_STRING 环境变量值传递,不做 shell 解释。
  • SEC-019:请求头内嵌换行的响应拆分攻击被消毒或拒绝。
  • SEC-020/021/022--maxforks=10下的超限请求全部 429 且现存连接不受影响;1MB+ 超大头部被 Go HTTP 服务器限制拒绝;Slowloris 慢速头部由 Go 内置超时兜底。

7.5 依赖与静态分析

  • SEC-024:检查 gorilla/websocket 版本及 CVE(issue #441)。
  • SEC-025:gosec SAST 扫描无 critical/high 发现(issue #418)。
  • SEC-026 帧大小限制:超过默认读取限制的帧导致连接关闭而非内存耗尽(issue #445 曾请求可配置帧大小——当前版本已提供--maxframesize,默认 1MiB,见 help.go)。

八、CGI 环境变量测试(ENV)

06-environment-cgi.md 的 20 条用例验证 RFC 3875 CGI 合规性。其核心洞察是:websocketd 把每个 WebSocket 连接当作一次 CGI 请求,通过环境变量向子进程注入全部请求上下文。

8.1 标准 CGI 变量(ENV-001)

连接env命令后,以下变量必须全部存在:

变量期望值
SERVER_SOFTWARE"websocketd/VERSION"
GATEWAY_INTERFACE"CGI/1.1"
SERVER_PROTOCOL"HTTP/1.1"
SERVER_NAMEHost 头中的主机名
SERVER_PORT端口号
REQUEST_METHOD"GET"
SCRIPT_NAME路径部分
REMOTE_ADDR客户端 IP
REMOTE_HOST主机名或 IP

8.2 请求上下文变量

  • ENV-002/003?key=value&foo=barQUERY_STRING原样注入;无查询串时置空。
  • ENV-004:目录模式下SCRIPT_NAME=/echo.shPATH_INFO=/extra/path
  • ENV-005/017REMOTE_ADDR/REMOTE_PORT有效,IPv6(::1)地址完整保留。
  • ENV-006:每次连接UNIQUE_ID唯一。
  • ENV-007REQUEST_URI=/path?query=1

8.3 HTTP 头转 HTTP_* 变量

  • ENV-008/014/015X-Custom-HeaderHTTP_X_CUSTOM_HEADER,规则为大写、连字符转下划线、加 HTTP_ 前缀;50+ 个头部无截断;CookieHTTP_COOKIE
  • ENV-009/010:SSL 下HTTPS=on,非 SSL 不设置。
  • ENV-011AUTH_TYPEREMOTE_IDENTREMOTE_USERCONTENT_TYPECONTENT_LENGTH按 RFC 3875 对 WebSocket GET 请求置空。
  • ENV-012/013--passenv=PATH透传 PATH(issue #144);含空格与引号的变量值原样保留。
  • ENV-016:Host 头解析由 http_test.go 的tellHostPort覆盖。
  • ENV-018:CGI 目录模式下 POST 请求设置CONTENT_LENGTH/CONTENT_TYPE
  • ENV-019(P0):父进程环境零泄漏——只出现 CGI 标准变量。这与 config.go 的平台相关defaultPassEnv(如 Linux 默认透传PATH,LD_LIBRARY_PATH,Windows 默认透传PATH,SystemRoot,COMSPEC,PATHEXT,WINDIR)共同构成完整的环境隔离策略。
  • ENV-020SERVER_SOFTWARE版本号与websocketd --version输出一致。

九、平台兼容性测试(Windows / Unix / 容器 / 跨平台)

9.1 Windows(07-platform-windows.md)

  • WIN-001/003/004.bat、PowerShell(powershell.exe -File echo.ps1)均可作为后端。
  • WIN-002 CRLF 处理\r\n尾随被trimEOL剥离(commit0559afd),客户端收到无回车符的干净文本。
  • WIN-007 进程终止:Windows 无 SIGTERM/SIGINT(issue #362),使用TerminateProcess等不同机制;断连后无孤儿进程。
  • WIN-008/009/013/014/015--maxforks生效、反斜杠路径与含空格路径(issue #293)、staticdir 的 Windows 路径、SSL、环境变量透传。
  • WIN-010/012:Windows 上 CGI 脚本(.bat/.exe,issue #454)、PHP(issue #320)。
  • WIN-005/006/011:VBScript/JScript 示例、32 位(windows_386)构建。

9.2 Unix(08-platform-unix.md)

  • macOS:Intel(darwin_amd64)与 Apple Silicon(darwin_arm64,GOARCH=arm64 go build,注意 issue #425 的 M1 Max 段错误须验证)。
  • Linux:amd64、ARM(树莓派,issue #295 安装脚本不识别 ARM)、ARM64(commitac4b25f6909932)、386;DEB/RPM 包安装;systemd 服务(issue #329);SIGTERM 优雅关闭并终止子进程。
  • 容器:Docker 内运行(issue #368 "input device is not a TTY")、无-t时 STDIN/STDOUT 管道不需要终端、Termux(Android,issue #452)。
  • 跨平台:MIPS 编译(issue #434)、进程组清理行为按 OS 记录(Linux/macOS 用信号,Windows 用 TerminateProcess)、Unix 无执行权限与 Windows 文件关联的差异。

十、协议与浏览器兼容性测试(PROTO / BROWSER / CLIENT)

10.1 WebSocket 协议(09-protocol-compatibility.md)

  • PROTO-001/002/003:版本 13(RFC 6455)完整支持;不支持的版本与缺失Sec-WebSocket-Key被拒绝。
  • PROTO-004 关闭码:1000/1001/1006/1011 均优雅处理,子进程被终止、日志记录原因(关联 issues #456、#399)。
  • PROTO-005/006/008:permessage-deflate 扩展(gorilla 可选压缩)、子协议协商(websocketd 不实现协商,头可能被忽略)、分片消息由库重组后完整送达子进程。
  • PROTO-007 大帧:64KB/1MB/10MB 帧,超限帧按库配置关闭连接。
  • PROTO-009 握手超时:慢速发送部分升级头最终超时,不无限等待(commitb2b6022加入握手超时)。

10.2 HTTP 版本

  • PROTO-010/011/012:HTTP/1.1 为标准传输;HTTP/1.0 可服务静态文件但 WebSocket 升级需要 1.1;HTTP/2 依赖 Go 服务器默认支持与库能力。

10.3 浏览器与客户端库

  • BROWSER-001~007:Chrome/Firefox/Safari/Edge/移动 Safari/移动 Chrome 全兼容;wss://安全连接;混合内容(https 页面连 ws://)被现代浏览器拦截。
  • BROWSER-009/010:开发控制台 UI 在各大浏览器可用(commitefd867b增加移动端 viewport),Tab 字符正确渲染(commit0e690fb)。
  • CLIENT-001~005:wscat、Pythonwebsockets库、Go gorilla/websocket 客户端、curl 7.86+ 手写升级请求、websocat 全部兼容。

十一、边界、性能与开发控制台测试

11.1 边界与错误(10-edge-cases-errors.md)

  • 输入边界:10MB 单行文本不截断;空白字符保留(只剥尾随换行);二进制模式 null 字节保留;文本模式帧内嵌\n成为进程的多个行;10000 条消息快速发送零丢失、有序。
  • 错误条件:进程写已关闭的 WebSocket 时被检测并终止(无错误循环);向已退出进程发送消息被静默丢弃或关闭连接;进程提前关闭 stdin(broken pipe)不崩溃;不读 stdin 的进程消息进入管道缓冲。
  • 竞态:进程退出与发送并发、关闭与输出并发、100 次快速重连——均无 panic、无 goroutine 泄漏、无死锁。
  • 缺失/畸形数据:缺 Host 被拒、空 Origin 不崩溃、畸形帧/错误掩码/不可能长度由 gorilla 库拒绝并关连接。
  • 资源限制ulimit -n 64下新连接优雅失败;内存压力下依赖 Go GC;SIGPIPE 由 Go 默认忽略。
  • 回归清单(P0)--ssl --port=8443--address的 nil 指针回归(issue #431/commit334a9ec,另见 #342);二进制帧加倍回归(commiteee5350,响应长度必须等于输入);断连后进程挂起回归(issue #159/commit3f89f2e,无僵尸进程)。

11.2 性能与扩展性(11-performance-scalability.md)

  • 并发连接:10/100/1000 并发(1000 需ulimit -n 4096,issue #356 曾报告 150 封顶);每秒 100 次连断持续 5 分钟无泄漏。
  • 吞吐与延迟:文本/二进制 10000 条消息吞吐;10MB 大消息完整性;本地回环往返延迟(期望亚毫秒级基线);首条消息延迟包含进程启动开销(issue #448);--reverselookup增加 DNS 解析延迟。
  • 资源:连接关闭后内存回落到基线(无稳态增长);goroutine 数回落(无泄漏);空闲时 CPU 近零。
  • 压力:50 连接 1 小时持续负载稳定;空闲 30 分钟后突发 100 连接无延迟;--maxforks=10满额下 100 个额外请求全部 429 且现存连接不受影响;静态文件服务不受 WebSocket 负载显著影响。

11.3 开发控制台(12-dev-console.md)

--devconsole内置的交互式测试控制台是快速验证端点的利器(访问http://[host]/foo即可测试ws://[host]/foo端点):

  • DEV-001~004(P0):页面加载(含连接/断开按钮、消息输入与日志区)、Connect/Disconnect、消息发送与回显。
  • DEV-005/006:上下方向键浏览消息历史、二进制消息显示。
  • DEV-007~009:URL 栏随 WebSocket 路径更新、Tab 字符渲染、移动端 viewport(commitefd867b)。
  • DEV-011~014:不加--devconsole时返回 404;与--staticdir并存时根路径优先级需文档化(help.go 明确二者不可同时使用);多窗口各自独立连接与子进程;服务重启后可重连。

十二、多语言示例测试(LANG)

13-examples-languages.md 覆盖仓库 examples/ 下的全部语言示例:Bash(greeter/count/send-receive/dump-env/chat)、Python、Node.js、Ruby、Perl、PHP、Java、C#、Rust、Lua、QuickJS(PR #396 新增)、Swift、Haskell,以及 examples/cgi-bin/ 的 CGI 示例和 examples/html/count.html 的 HTML 示例。

三条跨语言关注点是实战中最有迁移价值的结论:

  • LANG-200 缓冲刷新矩阵:Python(-uflush=True)、PHP(fflush(STDOUT))、Perl($| = 1)、Java(System.out.flush())、C(fflush(stdout)必须显式刷新;Bash(默认行缓冲)、Ruby(通常行缓冲)自动刷新。
  • LANG-201 退出码一致性:无论何种语言,websocketd 对退出码的处理行为一致。
  • LANG-202 UTF-8 保真:CJK、Emoji、多字节字符经各语言 stdin/stdout 原样保留(issue #348 中文问题为验证重点)。

十三、测试环境要求与自动化运行

13.1 环境矩阵(README 原表继承)

维度要求
操作系统Windows 10/11、macOS(Intel + ARM)、Ubuntu/Debian
浏览器Chrome、Firefox、Safari、Edge(均最新版)、移动 Safari、移动 Chrome
语言运行时Bash、Python 3、Node.js、Ruby、Perl、PHP、Go、Java、C#、Rust、Lua
工具wscat或同类 WebSocket CLI、curlopenssl
网络localhost、LAN、IPv4、IPv6

13.2 自动化测试基线

现有的 Go 测试套件覆盖单元级行为:

go test ./...

README 明确指出:本目录下的计划覆盖超出单元测试之外的手动、集成与探索性测试。仓库 qa/integration/ 中实际存在大量 Go 集成测试(如 core_test.go、process_test.go、cli_test.go、http_test.go、security_test.go、env_test.go、performance_test.go 等),与计划文件形成"自动化 + 人工验证"的双层保障:单元/集成测试守护回归,计划文件则为新特性验收、跨平台验证与安全审查提供结构化执行清单。

结语:把 QA 计划方法论迁移到自己的项目

这套计划的工程价值不止于 websocketd 本身,其方法论完全可复用:CATEGORY-NNN编号保证用例可追溯,用 P0–P3 优先级锚定发布门禁,用 Notes 字段沉淀回归历史,把每个历史 bug 固化为一条防复发用例。对于任何"外部命令 + 协议桥接"型服务(STDIN/STDOUT 转 WebSocket、CGI、进程编排网关),你都可以按"连接生命周期 → 进程管理 → 配置校验 → 路由 → 安全 → 环境隔离 → 平台矩阵 → 边界回归 → 性能压测"这条路径,复制出一套同样严谨、可执行、可验证的测试计划。

【免费下载链接】websocketdTurn any program that uses STDIN/STDOUT into a WebSocket server. Like inetd, but for WebSockets.项目地址: https://gitcode.com/gh_mirrors/we/websocketd

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询