4.4 KiB
4.4 KiB
WSS 协议要点
本文件记录 2026-07-06 手动浏览器 HAR、页面 JS 和 Go 版本当前实现的复核结论。
抓包结论
手动浏览器链路是 HTTP + WSS 混合:
- 页面初始化、商品信息、HttpDNS 等有多条
https://cdnws.api.huya.com/POST。 - 浏览器同时建立了 3 条
wss://77bc035c-ws.va.huya.com/连接。 scoreExchangePrize出现在 WSS 连接数据和静态 JS 中,没有出现在cdnwsPOST 请求中。- 当前 HTTP 版本可用,是因为
webActUI的 WUP over HTTP 编码已经对齐。 - Go 版 WSS 已改为浏览器同款
WebSocketCommand外层,仍需真实 Cookie 联调确认服务端返回。
连接
- WebSocket URL:
wss://<host>/?baseinfo=<base64 taf> - 手动 HAR host:
77bc035c-ws.va.huya.com - host 来自
launch.queryHttpDns或浏览器抓包,不应长期写死。 - 手动 HAR 中
baseinfo.cookie与traceId为空,cookie 通过后续VerifyCookie命令发送。 - 握手启用
permessage-deflate。 - 浏览器请求扩展:
permessage-deflate; client_max_window_bits - 服务端返回扩展:
permessage-deflate;server_no_context_takeover;client_no_context_takeover
正确外层结构
浏览器 JS 不是 1B version + 1B command + 4B sequence + body。
页面实际构造 TAF/JCE WebSocketCommand:
WebSocketCommand {
0: iCmdType int32
1: vData bytes
2: lRequestId int64
3: traceId string
4: iEncryptType int32
5: lTime int64
6: sMD5 string
}
WUP 请求发送逻辑:
Wup.setServant(servant)
Wup.setFunc(func)
Wup.setRequestId(requestId)
Wup.writeStruct("tReq", req)
WebSocketCommand.iCmdType = EWSCmd_WupReq(3)
WebSocketCommand.vData = Wup.encode()
WebSocketCommand.traceId = "<trace>:<trace>:0:<enableTrace>"
ws.send(WebSocketCommand.writeTo(JceOutputStream))
服务端返回 EWSCmd_WupRsp(4),内部 vData 才是 WUP 响应。
命令枚举
页面 JS 中可见的关键枚举:
3:EWSCmd_WupReq4:EWSCmd_WupRsp5:EWSCmdC2S_HeartBeat6:EWSCmdS2C_HeartBeatAck10:EWSCmdC2S_VerifyCookieReq11:EWSCmdS2C_VerifyCookieRsp16:EWSCmdC2S_RegisterGroupReq17:EWSCmdS2C_RegisterGroupRsp20:EWSCmdC2S_HeartBeatReq21:EWSCmdS2C_HeartBeatRsp23:EWSCmdC2S_UpdateUserExpsReq24:EWSCmdS2C_UpdateUserExpsRsp33:EWSCmdC2S_UpdateUserInfoReq34:EWSCmdS2C_UpdateUserInfoRsp
手动 HAR 解出的服务端 WSS 回包包括:
EWSCmdS2C_HeartBeatRspEWSCmd_WupRsp launch.wsLaunchEWSCmd_WupRsp mobileui.getConfigEWSCmd_WupRsp webActUI.getActPrizeListEWSCmd_WupRsp webActUI.getUserScoreEWSCmd_WupRsp webActUI.scoreExchangePrize
初始化流程
浏览器 WSS session 的关键流程:
- 连接
wss://<host>/?baseinfo=<base64 taf>。 - 发送
EWSCmdC2S_RegisterGroupReq(16),默认 group 为live:0。 - 通过 WSS 调用
launch.wsLaunch,手动 HAR 中 requestId 为-1。 - 发送
EWSCmdC2S_VerifyCookieReq(10),cookie 在这里进入 WSS 通道。 - 通过 WSS 调用
mobileui.getConfig。 - 发送
EWSCmdC2S_UpdateUserExpsReq(23),请求体是空 map。 - 再发送一次
EWSCmdC2S_RegisterGroupReq(16)。 - 发送
EWSCmdC2S_HeartBeatReq(20),后续维持心跳。 launch.queryHttpDns仍通过 HTTPcdnws调用。- 后续 WUP 业务在连接可用时走
signalSdk.sendWup,连接不可用时可 fallback 到sendWupHttp。
响应应按 WUP iRequestId 匹配回调,不能只用 FIFO。
活动接口
当前 Go HTTP 版本已实现:
webActUI.getActPrizeListwebActUI.getUserScorewebActUI.getUserPrizeRecordswebActUI.scoreExchangePrize
WSS 版本仍是实验状态,但外层 WebSocketCommand、初始化帧顺序和 requestId 匹配已按手动 HAR 修正。
抢购兑换请求结构:
tReq.user
tReq.sid
tReq.pid
tReq.ip = ""
tReq.clientEnv = {}
tReq.source = ""
tReq.isRole = 1
浏览器手动抢购小黄鸭成功回包确认:
webActUI.scoreExchangePrizesid=2203pid=12889status=200msg=请求成功exchangeInfo.pid=12889exchangeInfo.exchangeScore=988exchangeInfo.desc=兑换奖品:套装-潮萌小黄鸭
待完善
- 使用真实 Cookie 联调
list/score/exchange,确认服务端不再超时。 - 自动调用
launch.queryHttpDns获取最新 WSS host。 - 补更多基于真实抓包摘要的 WSS 编解码单测。