ws://{host}:{port}/dsuid: 用户唯一标识 (Required, 格式: 字母/数字/下划线, 1-50字符)token: 认证 Token (Required, 用于校验用户身份){
"mainCmd": 2,
"subCmd": 2,
"data": {
"tid": 0,
"code": 200,
"msg": "连接成功",
"data": {
"dsuid": "用户ID",
"timestamp": 1678888888,
"rooms": [1001, 1002]
}
}
}rooms 里没有 A(例如锁屏期间连接被清理),说明已不在该房,客户端应清除「在房」状态并提示「连接已恢复,请重新进入房间」或退回房间列表。rooms 非空,可与本地当前房间对比,一致则保持「在房」展示;不一致则以 rooms 为准。{
"mainCmd": <int>, // 主指令
"subCmd": <int>, // 子指令
"data": { // 业务数据
"tid": <int>, // 事务ID (可选,用于对应响应)
...
}
}{
"mainCmd": <int>, // 主指令
"subCmd": <int>, // 子指令 (通常与请求一致,或是特定的推送指令)
"data": {
"tid": <int>, // 对应的事务ID
"code": <int>, // 状态码 (200=成功, 400=请求错误, 401=未认证, 500=服务器错误)
"msg": <string>, // 提示信息
"data": { ... } // 业务响应数据
}
}mainCmd: 0, subCmd: 0mainCmd: 0, subCmd: 0{
"timestamp": 1678888888
}mainCmd: 2, subCmd: 12{
"code": 4001,
"msg": "账号在其他设备登录"
}code 为 4001 表示单点登录踢下线。3。subCmd: 1{
"roomid": 1001 // 房间ID
}subCmd: 1data.data:roomid: 房间IDseats: 全量麦位列表(按房间 roomlabel 决定数量,空麦位字段留空;roomlabel=1 为 0-8 共 9 个)online_count: 当前在线人数online_top3: 在线榜单前三名头像,[ {"headimgurl":"","name":""}, ... ] 最多 3 条mainCmd: 3, subCmd: 200 的麦位信息,格式同「麦位列表更新广播」(type: "mic_update", seats, locked_seats),便于前端统一用同一逻辑处理麦位展示。subCmd: 101{
"dsuid": "用户ID",
"action": "join",
"online_count": 123,
"online_top3": [ {"headimgurl": "https://...", "name": "昵称"}, ... ]
}subCmd: 2{
"roomid": 1001
}subCmd: 2subCmd: 102{
"dsuid": "用户ID",
"action": "leave",
"online_count": 122,
"online_top3": [ {"headimgurl": "https://...", "name": "昵称"}, ... ]
}subCmd: 3{
"roomid": 1001,
"content": "你好,大家好!"
}subCmd: 3{
"from_dsuid": "发送者ID",
"user_info": {
"dsuid": "发送者ID",
"nickname": "Tom",
"avatar": "http://...",
"sex": 1,
"nobility": 1,
"is_vip": true,
"role": 30 // 0:普通, 10:管理, 20:超管, 30:房主
},
"content": "你好,大家好!",
"type": "text",
"timestamp": 1678888888
}subCmd: 3 (仅发给请求者){
"code": 403,
"msg": "您已被本房间禁言" // 或 "您已被全服禁言", "内容包含敏感词"
}subCmd: 4{
"roomid": 1001,
"seat_index": 0 // 麦位索引 (0-8)
}subCmd: 4code: 200, msg: "上麦成功", data.players: 当前麦位列表code: 400msg: "该麦位已有人" — 麦位已被占用msg: "该麦位已锁定" — 房主/管理员已锁麦,普通用户不能上该麦msg: "麦位无效" — seat_index 不在 0-8msg: "你已经在麦上" — 当前用户已在其他麦位subCmd: 5{
"roomid": 1001
}subCmd: 5subCmd: 19{
"roomid": 1001,
"target_seat_index": 1 // 目标麦位索引 (0-8)
}subCmd: 19{
"code": 200,
"msg": "换麦成功"
}subCmd: 200{
"type": "mic_update",
"seats": [
{
"account": "用户ID",
"seat": 0,
"mic_status": 1,
"name": "昵称",
"headimgurl": "头像URL"
}
],
"locked_seats": [0, 2]
}roomlabel 决定数量;空麦位字段留空(account/name/headimgurl 为空,mic_status=0),有人/锁麦的才有完整字段。mic_status: 0=闭麦, 1=开麦, 2=封麦, 3=锁麦(空位锁定)。暂定 roomlabel=1 为普通模式,麦位 0-8 共 9 个。code: 403, msg: "无权操作"。subCmd: 6{
"roomid": 1001,
"type": "lock_seat | unlock_seat | kick | lock | mute | unmute | invite",
"seat_index": 0,
"target_dsuid": "用户ID"
}lock_seat — 锁麦:锁定空麦位,其他人不能上该麦;麦位有人时不可锁unlock_seat — 解锁麦位kick — 抱下麦:把该麦位上的人抱下麦lock — 封麦:禁言该麦位用户 (mic_status=2)mute — 闭麦:关闭该麦位用户麦克风 (mic_status=0)unmute — 解麦:开启该麦位用户麦克风 (mic_status=1)invite — 抱人上麦:指定用户上指定麦位,需传 target_dsuid;麦位已锁定时需先解锁invite 外必填invite 时必填,被抱上麦的用户 IDsubCmd: 6code: 200, msg: "xxx成功", type: "操作类型"code: 400"该麦位已有人" / "该麦位无人" / "麦位无效""该麦位已锁定" / "该麦位已锁定,请先解锁" (invite 时)"未指定用户" / "用户不在房间内" / "用户已在麦上" (invite 时)subCmd: 201 (仅 type=invite 时){
"type": "invited_on_mic",
"seat_index": 0,
"operator": "操作者ID"
}subCmd: 7{
"roomid": 1001,
"content": "跑马灯内容",
"scope": 1 // 1: 当前房间, 2: 全服广播
}subCmd: 7subCmd: 300{
"type": "marquee",
"content": "跑马灯内容",
"sender": "发送者ID",
"scope": 1,
"timestamp": 1678888888
}subCmd: 10{
"roomid": 1001,
"total_amount": 100, // 总金额(分/钻石)
"total_count": 10, // 红包个数
"wish_text": "恭喜发财"
}subCmd: 10subCmd: 400{
"type": "red_packet_notify",
"roomid": 1001,
"room_name": "房间名",
"sender_name": "发送者昵称",
...
}subCmd: 401{
"type": "red_packet_created",
"red_packet_id": "12345",
...
}subCmd: 11{
"roomid": 1001,
"red_packet_id": "12345"
}subCmd: 11data.data:amount: 抢到的金额remain_count: 剩余个数subCmd: 402 (有人抢到了红包)subCmd: 12{
"roomid": 1001
}subCmd: 12data.data.list: 红包列表数组subCmd: 8{
"roomid": 1001,
"target_roomid": 2002
}subCmd: 9{
"roomid": 1001,
"target_roomid": 2002
}subCmd: 57: PK 邀请 (收到别人的PK邀请)subCmd: 58: PK 已接受subCmd: 59: PK 已拒绝subCmd: 60: PK 邀请已取消subCmd: 61: PK 匹配状态更新 (status: 1=开始匹配, 0=取消匹配)subCmd: 62: PK 开始 (包含双方房间信息)subCmd: 63: PK 结束 (包含结果)subCmd: 64: PK 实时数据更新 (分数/贡献值变化)subCmd: 13{
"roomid": 1001,
"password": "xxxx"
}subCmd: 13subCmd: 202{
"type": "room_info_update",
"data": {
"passwdStatus": "1"
}
}subCmd: 14{
"roomid": 1001
}subCmd: 14subCmd: 202{
"type": "room_info_update",
"data": {
"passwdStatus": "0"
}
}subCmd: 15{
"roomid": 1001,
"target_dsuid": "user_id",
"job_type": 10 // 10: 管理员, 20: 超级管理员, 0: 取消职位
}subCmd: 15subCmd: 203{
"type": "room_job_update",
"roomid": 1001,
"target_dsuid": "user_id",
"job_type": 10
}subCmd: 16{
"roomid": 1001,
"target_dsuid": "user_id"
}subCmd: 16{
"code": 200,
"msg": "踢出成功"
}subCmd: 16{
"code": 200, // 注意这里不是错误码,而是特定业务通知
"msg": "您已被移出房间,60分钟内无法再次进入",
"ban_minutes": 60
}subCmd: 204{
"type": "kick_user",
"operator_dsuid": "operator_id",
"target_dsuid": "target_id",
"ban_minutes": 60
}subCmd: 17{
"roomid": 1001,
"target_dsuid": "user_id"
}subCmd: 17subCmd: 205{
"type": "blacklist_add",
"operator_dsuid": "operator_id",
"target_dsuid": "target_id"
}subCmd: 18{
"roomid": 1001,
"target_dsuid": "user_id"
}subCmd: 18game_server_broadcast 或 lobby_server_broadcast 触发,WebSocket 解析后推送给对应房间或用户。mainCmd: 2, subCmd: 4(仅推送给该房间内用户)| 字段 | 类型 | 说明 |
|---|---|---|
| sendaccount | string | 送礼用户 ID |
| acceptaccount | string | 收礼用户 ID |
| giftid | string | 礼物配置 ID |
| giftname | string | 礼物名称 |
| sendnum | string | 赠送数量 |
| sendtype | string | 送礼类型(如 2=麦上的人,3=房间所有人) |
| totolmoney | string | 总价值(如钻石/金币) |
| data | string | 扩展数据(JSON 字符串,含礼物配置等) |
| roomid | string | 房间 ID |
| roomtype | string | 房间类型 |
| jsqtzstatus | string | 计算/统计状态(如是否最后一笔) |
| blindboxstatus | string | 盲盒状态(0=否,1=是) |
{
"mainCmd": 2,
"subCmd": 4,
"data": {
"sendaccount": "10001",
"acceptaccount": "10002",
"giftid": "gift_001",
"giftname": "玫瑰",
"sendnum": "10",
"sendtype": "1",
"totolmoney": "1000",
"data": "{\"giftmoney\":100,...}",
"roomid": "1001",
"roomtype": "120",
"jsqtzstatus": "1",
"blindboxstatus": "0"
}
}mainCmd: 2, subCmd: 18subCmd: 4 一致,用于盲盒、全房间广播等场景。客户端可按同一结构解析并展示动画/跑马灯等。mainCmd: 2, subCmd: 9(仅推送给该房间内用户){
"mainCmd": 2,
"subCmd": 9,
"data": {
"roomid": "1001",
"roomtype": "120"
}
}subCmd: 4 / 18 做礼物动画或列表更新,再在收到 subCmd: 9 时拉取或刷新房间整体数据。subCmd: 2: 连接成功(见第 1 节)subCmd: 11: 全服通用广播(如个人资料刷新)subCmd: 47: 游戏/房间广播,data: {"roomid": ..., "data": ...}subCmd: 50: 大厅/需求广播subCmd: 62: 房间服务数据更新(通用 JSON 数据推送)subCmd: 70: 房间话题标题更新,data: {"roomid", "roomtype", "roomnoticetitle"}subCmd: 71: 房间话题内容更新,data: {"roomid", "roomtype", "roomexplain"}subCmd: 72: 房间公告更新,data: {"roomid", "roomtype", "roomnotice"}subCmd: 73: 房间名称更新,data: {"roomid", "roomtype", "roomname"}| Code | 说明 |
|---|---|
| 200 | 成功 |
| 400 | 请求参数错误 / 业务逻辑错误 |
| 401 | 未认证 / Token 无效 |
| 402 | 余额不足 |
| 4001 | 单点登录:账号在其他设备登录(被踢下线) |
| 4002 | 您已不在房间内,请重新进入房间(见下方说明) |
| 403 | 无权限 / 禁言等 |
| 413 | 消息过大 |
| 500 | 服务器内部错误 |
data.rooms 同步界面,可能仍显示「在房间内」,但 Redis 中该用户已不在房间成员列表,此时进行上麦、下麦、发消息等操作会收到 code: 4002。用户再次进房后仍会看到自己在原麦位,其他人在此期间看到的麦位也不变。data.code === 4002,data.msg === "您已不在房间内,请重新进入房间"(各 subCmd 的响应里均可能携带)。data.rooms。若本地有「当前房间」但 rooms 中不包含该房间(常见于锁屏/断线重连后被服务端清理),应立即清除本地在房状态并提示「连接已恢复,请重新进入房间」或退回房间列表,这样不会出现“界面还在房内”的错觉。code === 4002 时,提示用户「您已不在房间内,请重新进入房间」。brokenLineReconnection),判断用户断线前是否在语音房内。dsuid( 及登录态)。code: 200,data 含:in_voice_room: truerooms: 断线前所在房间 ID 数组,如 [1001]roomid: 首个房间 ID,便于直接重进该房data 为空或走其他断线重连逻辑)。data.in_voice_room === true 且 data.rooms.length > 0,可提示「是否重新进入房间」并带 data.roomid,用户确认后建立 WebSocket 并发送「加入房间」(subCmd: 1, roomid)。