AIClaw 会话连续性技巧:/new与/continue在消息渠道中的用法
把 AI Agent 接到企业微信、飞书、Telegram 这类消息渠道里,真正难的往往不是“能不能收发消息”,而是“会话到底怎么接上”。
网页聊天界面天然有会话列表,用户可以点回旧对话继续做事;但在消息渠道里,用户看到的通常只有一个线程、一串消息,最多再带一个发送者标识。如果系统不能把这个外部线程稳定映射回内部会话,结果一般只有两种:上下文丢失,Agent 每次都像第一次见你;或者会话越来越乱,不知道当前线程到底接的是哪段历史。
AIClaw 在这一层没有停留在“适配几个 webhook / websocket”上,而是把渠道会话连续性做成了运行时能力:外部线程绑定内部会话、归档历史可恢复、用户还能直接在渠道里发 /new 和 /continue 控制会话。
这篇文章不讲“新发布了什么炫功能”,而是拆一下这个设计为什么实用。
先看问题:渠道消息为什么天然容易丢上下文
一个最基础的渠道集成,通常只做三件事:收到外部平台的入站消息、把消息转给指定 Agent、再把回复发回原渠道。如果只是做一问一答,这已经够了。
但真实使用里,很快就会出现这些需求:
- 我想从当前线程开启一个全新的任务
- 我不想删掉旧会话,只是别把旧上下文继续带进来
- 我想把之前归档的一次任务接着聊下去
- 同一个外部线程必须稳定对应同一个内部 conversation
- 第一批消息并发到达时,不能创建出两条重复会话
这些问题如果交给 Prompt 去“猜”,最后通常都不稳定。AIClaw 的做法是放到 channel runtime 里明确处理。
核心机制:把外部 thread 绑定到内部 conversation
AIClaw 在处理渠道入站消息时,会先从消息事件里提取 thread lookup keys。来源可能包括:渠道原生线程 ID、线程别名,如果没有线程概念,则退化到 sender ID。这些 key 会写入 channel_threads 映射表,核心关系就是 channel_id、thread_key、conversation_uuid。
后面同一个线程再发消息,系统先查这个映射:找到了,就继续原会话;没找到,就新建 conversation 并绑定当前线程 key。
这层设计的价值很直接:外部线程和内部会话的关系是显式的,一个线程不会莫名切到别的上下文,渠道聊天也能进入 AIClaw 正常的会话、消息、执行日志体系。
另外,AIClaw 还做了并发保护。针对同一个 (channel, thread) 键集合,运行时会用 singleflight 合并首次建会话操作,避免并发首包把同一线程拆成多条 conversation。这点非常工程化,但也非常关键。
在渠道里直接控制会话:/new、/continue、/archives
这块最值得写,因为它解决的是“用户到底怎么用”。AIClaw 会在真正进入 LLM 调用前,先拦截内置斜杠命令,目前包括:/new、/reset、/continue、/continue N、/archives、/help。也就是说,用户不需要回到后台页面切换会话,直接在企业微信或飞书里发命令就能控制上下文。
/new:在当前线程开一个干净的新会话
/new 的语义不是“清空所有历史”,而是:解绑当前线程和旧 conversation 的关系,新建一个 conversation,把当前线程 key 重新绑定到这个新会话。旧会话本身不会被删除,后面还能找回来。这个行为很符合渠道场景——用户说“开个新会话”,通常是想把当前任务切开,而不是想毁掉之前的工作记录。
/continue:把当前线程切回旧会话
/continue 会列出最近的会话归档,用户可以再通过 /continue N 选择其中一条,把当前线程重新绑定到那次历史 conversation。绑定成功后,用户继续在同一个外部线程里发消息,Agent 接上的就是旧任务上下文,而不是重新开始。这意味着消息渠道虽然没有复杂 UI,但依然获得了“恢复旧会话”的能力。
/archives:渠道里的“最近会话”入口
/archives 本质上和不带参数的 /continue 一样,都是列出最近归档。这里还有一个细节很重要:归档列表会按 userID 过滤——AIClaw 不会把别人的渠道历史混进你的继续列表里。
为什么 /continue 不是直接扫数据库,而是依赖归档
AIClaw 的继续会话能力,不是简单把数据库里的历史全扔给用户选。它会在消息数达到阈值后,自动为会话生成 Markdown 归档,而且这个归档不再额外调用模型。归档内容主要提炼用户目标、工具使用统计、最近的重要决策。归档文件按 agent 维度落在 workspace 里,/continue 列表按更新时间倒序展示。
这么做有几个好处:成本低,不需要为了归档再跑一次 LLM;可检查,归档本身就是普通 Markdown;更适合渠道场景,用户要的是“最近做过什么、从哪条接着来”,不是完整数据库明细。
一个很实际的使用流程
举个接近日常运维或研发协作的例子:
- 团队成员在企业微信线程里让 AIClaw 排查一次部署问题
- AIClaw 把这个线程绑定到某个 conversation,后续消息都延续同一上下文
- 问题处理完后,用户发
/new,在同一线程里开启一个新的独立任务 - 第二天想继续昨天的部署排查,就发
/continue - 选择对应编号后,当前线程重新绑定到旧会话
- 下一条消息直接接着昨天的上下文继续,而不是从零开始
这种体验的重点不是“功能多高级”,而是它足够顺手,符合大家已经习惯的消息渠道工作方式。
这套设计值得肯定的地方
总结下来,AIClaw 在这个点上做得比较扎实,原因主要有四个:
- 会话控制放在 runtime 层,不靠 Prompt 硬撑
- 外部线程和内部 conversation 是明确映射关系
- 归档是低成本、可落盘、可检查的
- 用户命令非常短,适合在消息渠道里直接使用
更重要的是,它承认了一件现实:很多团队真正操作 Agent 的第一入口,不是网页后台,而是消息渠道本身。既然如此,渠道集成就不应该只是“把回复发出来”,而应该具备明确的会话语义。AIClaw 的这套 /new + /continue + 线程绑定设计,本质上就是在补这个关键能力。
AIClaw 是一个开源、自托管的 AI Agent 平台,后端使用 Go,管理端使用 Vue。它把内置工具、自定义 HTTP/命令工具、MCP 工具、运行时计划、子 Agent、持久记忆、执行日志和多消息渠道集成放进了同一个可部署系统里。
