超级群类型迁移与兼容 FAQ
rev22 引入 SUPER_GROUP(10) 后,线上会同时存在两种表示:存量数据(GROUP(2) + groupType=super)与新数据(10)。本页回答迁移期最常见的兼容问题,并给出各端统一的判断与展示口径。
现在应该用 2+groupType 还是 10?
契约要求新消息使用 10。客户端在发送超级群消息时传 SUPER_GROUP(10);读取时必须同时接受 2 与 10。若当前 SDK/服务端还未升级到 rev22(调用 10 返回 1001 invalid conversationType),先继续用 2+super 兼容写法,升级后再切写 10。
同一个超级群会出现两条会话吗?
不会。会话键按 groupId 聚合(g:{groupId}),2 与 10 指向同一会话。会话对象的 conversationType 可能是 10(新会话)或 2(存量会话),取决于会话首次创建时的类型;后续消息不会把会话改写为另一种类型。历史、未读、回执、撤回等群语义完全一致。
历史消息能按 10 读吗?存量消息会丢吗?
不会丢。历史读取以会话键为准:传 2 或 10 都读取同一群会话的历史,返回的每条消息自带其发送时的 conversationType(2 或 10)。按 seq 排序渲染即可,不要按 conversationType 过滤掉另一种取值。
会话列表里怎么判断一个会话是超级群?
优先读会话的 groupType:群类会话(2 或 10)返回 "normal"|"super",10 恒为 super。兜底条件:conversationType === 10,或 conversationType === 2 && groupType === "super"。不要只判断 conversationType === 2。
未升级的旧客户端收到 10 会怎样?
取决于旧版本实现:宽松实现会把未知类型当普通会话或直接忽略;严格实现可能丢弃或报错。因此升级顺序建议:先升级“读”兼容的客户端,再让服务端/新客户端开始产生 10。无法升级的旧版本应保持在 2+super 的写入路径上。
服务端回调里的字段是什么?有 channelType 吗?
服务端回调(22 类事件)的载荷使用 conversationType,取值可能是 10 或存量 2;回调载荷没有 channelType 字段。机器人/集成回调是另一套载荷,使用 channelType:PERSON / GROUP / ULTRAGROUP / TEMP_GROUP,10 与存量 2+super 都映射 ULTRAGROUP。
控制台/报表怎么统计超级群消息?
迁移期用双口径:conversationType=10 加上 conversationType=2 且群 groupType=super 的部分。控制台消息追踪按 conversationType 数值展示;若控制台版本未升级,10 可能显示为原值(不影响数据)。统计口径应在报表层统一,而不是改写存量消息。
频道消息怎么和群消息区分?
rev23 起看消息的 channelId:有值 = 频道消息(仅频道成员接收、历史可按频道过滤),无值 = 群级消息。发送时传 options.channelId 即发频道消息;不带则为群级。频道消息仍属于群会话,未读/回执按群会话聚合。详见「超级群频道级消息」。
迁移需要改数据库/重发消息吗?
不需要。存量会话与消息保持原样即可读;新消息写 10。展示层按“双表示兼容”判断,统计层按双口径汇总。只有业务强依赖“消息类型必须为 10”时才需要自行迁移(不推荐,风险高于收益)。
回滚方案是什么?
客户端回滚到旧版本后仍能读 2+super 的存量数据;但已经写入 10 的新消息/新会话在旧版本中的表现取决于其兼容实现。因此灰度期间建议:先小流量验证旧版本对 10 的容错,再扩大范围;服务端无需回滚(10 与 2 共用会话键)。
SDK 升级后发送仍失败 1001?
检查三件事:① SDK 是否为包含 rev22 的版本(提供 SUPER_GROUP 常量);② 服务端是否升级(10 合法、按群语义处理);③ 传入的 groupId 是否是超级群(普通群也会接受 2/10 群语义,但产品上不要混用)。
iOS / HarmonyOS 怎么处理?
两端是契约预留(声明同构、无运行时代码)。升级时按 additive 契约同步枚举声明;接入运行时后再按本页兼容规则实现判断函数。
统一判断函数(三端)
把“是否超级群”收敛为一个函数,避免各页面重复写条件;升级到 rev22 后只需改这一处。
// 兼容两种表示:10(rev22)或 2 + groupType=super(存量)
export function isSuperGroup(conversation) {
if (!conversation) return false;
if (Number(conversation.conversationType) === 10) return true;
return Number(conversation.conversationType) === 2 && conversation.groupType === "super";
}
// 消息级判断(历史/回调里消息自带 conversationType)
export function isSuperGroupMessage(message, groupTypeByGroupId) {
if (!message) return false;
if (Number(message.conversationType) === 10) return true;
if (Number(message.conversationType) !== 2) return false;
return groupTypeByGroupId(message.targetId) === "super";
}static boolean isSuperGroup(Conversation conversation) {
if (conversation == null) return false;
if (conversation.getConversationType() == ConversationType.SUPER_GROUP) return true;
return conversation.getConversationType() == ConversationType.GROUP
&& "super".equals(conversation.getGroupType());
}
// 消息级:10 直接判定;2 需要群属性兜底(由业务缓存提供)
static boolean isSuperGroupMessage(Message message, java.util.function.Function<String, String> groupTypeOf) {
if (message == null) return false;
if (message.getConversationType() == ConversationType.SUPER_GROUP) return true;
if (message.getConversationType() != ConversationType.GROUP) return false;
return "super".equals(groupTypeOf.apply(message.getTargetId()));
}bool isSuperGroup(Conversation conversation) {
if (conversation.conversationType == RongIMConversationType.SUPER_GROUP) return true;
return conversation.conversationType == RongIMConversationType.GROUP &&
conversation.groupType == "super";
}字段与映射速查
| 场景 | 字段 | 取值 | 处理 |
|---|---|---|---|
| 会话视图(getConversationList / getConversation) | conversationType | 1 / 2 / 3 / 4 / 10 | 10 与 2+super 都当超级群 |
| 会话视图 | groupType | normal / super / null | 群类会话(2/10)非空;单聊/聊天室/系统为 null |
| 消息(历史 / MESSAGES 事件) | conversationType | 2 或 10 | 按 seq 排序,不要过滤另一取值 |
| 消息(rev23 频道消息) | channelId | 存在 = 频道消息;不存在 = 群级 | 发送传 options.channelId;历史可加 channelId 过滤 |
| 服务端回调(22 类) | conversationType(频道消息另带 channelId) | 2 或 10 | 无 channelType 字段 |
| 机器人 / 集成回调 | channelType | PERSON / GROUP / ULTRAGROUP / TEMP_GROUP | 10 与 2+super → ULTRAGROUP;频道消息另带 channelId |
| Open API 群消息发布 | conversationType(可选)/ groupType / channelId(可选) | 缺省按群属性推导:super→10、normal→2 | 带 channelId 时按频道投递;普通群带 channelId → 1001 |
迁移检查清单
- 读兼容:所有渲染/统计/权限判断处使用统一 isSuperGroup,接受 2 与 10。
- 写切换:发送超级群消息传 10;发送普通群仍是 2。
- 展示:会话列表/聊天页的群样式同时覆盖 2+super 与 10;IMKit 版本需支持 rev22。
- 回调:按 conversationType 归档;机器人回调按 channelType=ULTRAGROUP 归类。
- 统计:超级群口径 = 10 + (2 且 groupType=super),在报表层归一。
- 灰度与回滚:小流量验证旧版本对 10 的容错,再扩大;服务端无状态迁移。
- 验证:用同一 groupId 分别以 2 与 10 发送,确认落到同一会话、历史连续、未读与已读连续。
相关链接
- 超级群会话类型:语义、发送/历史规则与限制
- 超级群场景指南
- 服务端回调:22 类事件与载荷字段
- ConversationType 枚举