← 所有文章
指南

Telegram 群组升级为超级群组:安全更新 Chat ID

Telegram 群组迁移为超级群组后,机器人后续发送应使用新的聊天标识。Bot API 的服务消息可包含 migrate_to_chat_idmigrate_from_chat_id,失败的 API 响应也可能包含 parameters.migrate_to_chat_id。应明确记录旧 ID 到新 ID 的关系:更新未来的发送目标,但保留历史消息原本所属的聊天标识。

要点

  • 群组迁移改变的是目标身份,不等于 webhook 投递故障。
  • 读取结构化迁移字段,不要匹配错误文案或猜测新 ID。
  • 历史记录保留原始聊天身份;新发送在执行前解析当前目标。
  • UnifyPort 公开的标准事件结构没有承诺相同的迁移映射,不能直接套用 Bot API 字段。

migrate_to_chat_id 与 migrate_from_chat_id 分别表示什么

Telegram 官方 Bot API 文档Message 中定义了两个可选字段,并在 ResponseParameters 中定义了迁移目标字段:

证据旧聊天新聊天
消息包含 migrate_to_chat_id该消息的 chat.idmessage.migrate_to_chat_id
消息包含 migrate_from_chat_idmessage.migrate_from_chat_id该消息的 chat.id
失败响应包含 parameters.migrate_to_chat_id原请求使用的数字聊天 IDparameters.migrate_to_chat_id

处理错误响应时必须保留原请求上下文。如果请求使用的是用户名,而不是已保存的数字 ID,不能仅凭错误响应编出旧聊天的数字标识。

Telegram 提醒,这些迁移 ID 可能超过 32 个有效位,但最多为 52 个有效位;有符号 64 位整数或双精度浮点数可以安全保存。检查整个链路,避免任何 32 位转换。应用内部的键也可以选择十进制字符串,但必须完整保留符号和值。

本文假设接收端已经收到更新。如果尚未确定身份和传输方式,请先看 Telegram Bot API webhook 与统一入站 webhook 的区别

把迁移建模为别名,不要重写历史

建议在应用中分开保存“业务会话”和“平台发送目标”。在租户及机器人集成范围内维护旧 ID 到新 ID 的映射,并保存建立关系的证据。这些是本地存储设计,不是新增的 Telegram API 字段。

不要批量替换历史消息记录中的聊天 ID。Telegram 的 message_id 是在所属聊天内唯一,而非全局唯一。把旧消息重新标成新聊天下的消息,可能导致错误关联。聊天目标之间的别名关系,不代表消息 ID 之间存在官方保证的转换。

推荐处理顺序:

  1. 验证来源并持久保存收到的更新;若来自 API 错误,则保存实际响应及请求上下文。
  2. 根据上表提取旧、新聊天标识。
  3. 在存储支持的情况下,以同一事务写入映射并更新当前路由。
  4. 同一映射重复出现时不再产生动作;遇到冲突或循环关系,暂停并交由人工核查,不要静默覆盖。
  5. 保持历史记录不变;队列任务真正发送前,再解析当前目标。

映射更新与目标解析应使用应用锁或等效并发控制协调。否则,一个工作进程可能刚读到旧 ID,另一个就提交了迁移。即使有本地协调,也仍需处理这种竞争导致的发送错误。

恢复排队发送,而不是盲目重试

失败响应中的 parameters.migrate_to_chat_id 提供了新目标。先持久保存,再判断是否需要重试,并检查任务是否仍适合执行。网络超时是另一类情况:它既不能证明发生了迁移,也不能证明消息未发出。

如果任务引用较早的消息,不要直接把旧 message_id 搭配新聊天 ID 使用。应确认引用仍然有效,或将任务交由人工处理;不要悄悄把依赖上下文的动作改成另一条普通消息。

需要记录发送结果时,可参考 webhook 响应内回复与独立 sendMessage 请求的比较。成功确认入站投递,不等于出站任务已经完成。

以下是建议的验收测试,不是已测得的结果:

  • 重复迁移证据只保留一条映射,不创建第二个发送任务。
  • 迟到的旧聊天更新仍保留原始归属,不把当前目标改回旧 ID。
  • 冲突映射会暂停相关任务。
  • 同名但无关的群组不会被合并。
  • 标识经过序列化和数据库读写后没有被截断。

UnifyPort 的能力边界

UnifyPort 的非官方接口通过 message.received 提供 provideraccount_iddata.conversation.id。这些标识应保存在独立命名空间中,不要假设可直接替换为 Bot API chat ID。

公开事件文档没有定义 migrate_to_chat_idmigrate_from_chat_id,也没有保证提供新旧迁移关系。不能把 group.updatedconversation.updated 当作这种保证。对于已连接的 Telegram 消息账号,应依据会话列表接口返回的 conversation_id 做核对。同名只是线索,不是会话延续的证据;无法确认的映射需要人工审查。

接收事件时配置 signing_secret,并遵循 webhook 投递验签文档。UnifyPort 不提供 REST 消息历史读取 API,也不保证补发错过的事件。查询当前会话列表不能重建丢失消息,更不能提供未被文档定义的迁移关系。

常见问题

群组升级后需要修改 webhook URL 吗?

新 chat ID 是路由问题,本身并不说明 webhook 地址需要更换。先检查收到的更新和保存的发送目标。

能从旧 ID 推算新 ID 吗?

使用 Telegram 提供的迁移字段。不要添加前缀或修改数字来构造目标。

是否应该把所有历史消息移到新 chat ID?

不应直接改写原始聊天与消息的组合。可以在业务层关联两个会话,但不能宣称消息标识也完成了转换。

UnifyPort 会自动暴露这些 Bot API 迁移字段吗?

公开契约没有承诺这种行为。请按其自身 API 核对已连接账号的会话标识,对不确定映射进行审查。

下一步与来源

检查发送端在何处解析目标,尤其是排队任务。需要核对已连接账号的会话时,从会话列表文档开始。

UnifyPort API

让消息接入变成一条稳定的产品管线。

先用统一 API 跑通发送,再用标准事件把所有入站消息接回业务系统。