WhatsApp 清空与删除聊天:如何同步正确的 Webhook 状态
清空 WhatsApp 聊天会清除本地历史,但保留聊天;删除聊天则是另一种聊天列表操作。在 UnifyPort 中,conversation.cleared 和 conversation.deleted 分别报告已连接消息账号的这些变化。两者都不代表为所有人删除消息。共享收件箱应分开管理历史内容与会话的可见性,再按明确的策略处理自己保存的副本。
要点
- 这是账号本地变化的通知,不是删除客户消息的命令。
- 目标聊天由
data.conversation.id标识,不是顶层事件id。 delete_media描述本地媒体删除,不证明对象存储或 CRM 中的副本已清理。- 阻止旧历史重新显示,不应等于永久拒绝该会话的新消息。
清空聊天、删除聊天与撤回消息有什么区别?
WhatsApp 的清空聊天说明指出,清空不会把聊天移出聊天列表,也不会使你退出群组。删除聊天说明则将删除视为另一项操作,并说明删除群聊前需要先退出群组。接入时不要把其中任何一个操作解释成“删除所有业务系统中的一切”。
| 观察到的事件 | 文档定义的范围 | 建议的收件箱行为 |
|---|---|---|
conversation.cleared | 已连接账号清空本地历史;远端会话及群成员身份不变 | 保留会话入口,按策略隐藏受影响的本地历史 |
conversation.deleted | 已连接账号在本地删除会话 | 从常规镜像列表中移除,仅保留策略允许的核对元数据 |
message.deleted | 单条消息被删除或撤回 | 定位具体消息,不处理整个聊天 |
conversation.updated | 本地聊天设置发生变化 | 只更新提供的设置,不推断历史被删除 |
最后一列是应用设计建议,并非 UnifyPort 自动执行的操作。如果目标是撤回已发送消息,请阅读编辑、撤回与本地隐藏的区别。会话删除事件不是撤回请求的回执。
按会话事件解析,不要套用消息载荷
清空事件文档与删除事件文档提供会话目标及 delete_media,没有提供受影响消息 ID 清单,也没有定义精确的历史截断位置。
以下是使用真实字段与虚构标识符的示例,不是实际抓取的流量:
{
"id": "evt_c4d0b7a2e5",
"type": "conversation.cleared",
"provider": "whatsapp",
"account_id": "acc_8c21d0",
"occurred_at": "2026-10-29T08:15:00Z",
"data": {
"conversation": {
"id": "8600000000000@s.whatsapp.net",
"type": "user"
},
"delete_media": true,
"event": { "kind": "conversation_cleared" }
}
}
本地查询应同时限定工作空间、渠道、account_id 与 data.conversation.id。保留接收到的标识符,不要从手机号拼接,也不要因聊天标题相同而合并。这个分支处理的是会话事件,不应要求 data.message.id。
渠道事件矩阵目前将这两个事件映射到 whatsapp,不包含独立的 whatsapp-protocol 或所有其他渠道。矩阵说明解析器支持,并不保证每个上游账号或部署都会产生事件。
将三类应用状态分开保存
先确定产品承诺,再实施清理。镜像收件箱可以跟随账号隐藏本地历史;受独立规则管理的业务档案可能有不同的保留要求。应向操作员说明差异,不能默默把原生清空解释成“无需处理”或“删除所有业务记录”。
在自己的存储中分别维护:
- 会话列表可见性:会话是否出现在镜像列表。
- 历史可见性及清理状态:哪些旧内容被隐藏,哪些自有副本仍待清理。
- 后续消息接纳规则:何时允许新活动重新打开会话,同时不恢复旧历史。
这些是建议的本地概念,不是新增 Webhook 字段。保存最小化的账号范围标记与清理决定,而不是删除所有会话身份信息,否则延迟历史批次可能重新创建可见记录。
两类事件都应遵循Webhook 投递契约:配置 signing_secret,针对 X-Device-Timestamp、一个点和原始请求体计算 HMAC-SHA256,并检查时间戳新鲜度。在一个本地事务中完成普通事件去重、可见性变更和清理任务入队;持久化接收后返回 2xx,不必等待所有外部系统完成。
不要让历史补录撤销清空决定
投递顺序没有保证。occurred_at 记录事件发生时间,但清空/删除契约未将它定义为所有受影响消息的精确截止时间。HTTP 到达时间也不能证明内容是新消息。
可采用以下保守策略:
| 后续输入 | 隐藏规则仍有效时的建议处理 |
|---|---|
| 同一清空或删除事件重试 | 保持原决定,继续未完成的清理 |
| 历史批次包含已隐藏内容 | 不自动重新发布 |
| 实时事件包含已隐藏的消息 ID | 保持隐藏 |
| 看似新消息,但无法判断与清空的先后关系 | 暂停自动回复并复核范围 |
| 已确认的新会话活动 | 按明确规则重新显示会话,不恢复旧历史 |
已知消息 ID 可以保护已存内容,却无法识别从未收到过的旧消息。缺少可信边界时,应选择显式复核或保守隐藏,不要声称能完美还原时间顺序。新的事件 ID 本身不代表新的消息内容。
如果收件箱支持加载历史,应把此规则加入WhatsApp 按需历史加载的合并流程。历史批次需要逐条消息合并,仅按顶层事件 ID 去重可能丢弃合法分块。加载历史不能隐式重置清空决定。
媒体清理与验收
delete_media=true 表示本地媒体也已清除或删除,不证明你下载的附件、搜索条目、AI 上下文或转发副本已被删除。false 也不等于允许无限期保留所有内容。应执行已向用户说明的保留及访问策略,分别跟踪清理完成状态和 Webhook 确认。
使用自己控制的账号测试:
- 清空历史后仍保留会话入口,但被隐藏内容不参与搜索。
- 删除会话后镜像列表隐藏它,不自动屏蔽联系人或请求退群。
- 旧历史批次或重复事件到达后,不自动恢复内容。
- 确认的新活动可以按规则重新打开会话,但不带回旧历史。
- 媒体清理失败时显示“清理待完成”,而非“已彻底删除”。
这些是建议测试,不是已取得的结果。UnifyPort 提供非官方接口,没有保证重放,也没有返回消息历史的 REST 读取 API。未收到事件不证明未发生本地变化。
常见问题
conversation.deleted 会删除对方的消息吗?
不会。文档定义的是已连接账号本地删除会话,不是为所有人删除。
conversation.cleared 是否代表退群?
不是。文档明确说明群成员身份不变。
能根据这些事件实现清空聊天 API 按钮吗?
事件文档描述观察结果,不是发起清空或删除的接口。不要从事件名称推导不存在的 endpoint。
下一步与来源
先阅读 conversation.cleared 文档,明确可见性、保留和重新打开规则,再接入破坏性清理。
资料核对日期:2026-10-29。
让消息接入变成一条稳定的产品管线。
先用统一 API 跑通发送,再用标准事件把所有入站消息接回业务系统。