九维我操你爹
Anthropic 和 OpenAI 在这两天分别发布了报告描述自家平台是如何对抗外国敌对势力和公司对自家平台的滥用的

其中,Anthropic 的报告指出他们通过追踪元数据,成功识别了 DeepSeek,Moonshot AI 和 Minimax 对他家模型的蒸馏,甚至能准确溯源到特定的实验室人员和公司高级员工

OpenAI 的报告则更为详细,不仅指出有中国网络战人员使用 OpenAI 的产品,还详细描述了他们输入的内容和进行的操作,例如对高市早苗进行舆论攻击以及在 Twitter 上攻击“李老师不是你老师”等账号

防止自家的服务被滥用是天经地义的,但是这里有一个问题:

Anthropic 和 OpenAI 不仅看了用户的聊天内容,用聊天内容和元数据对用户做了大数据分析,还把聊天和分析的内容公之于众

换句话说,用户在这些平台上并没有什么隐私——平台可以随意查看和审查你的聊天内容,根据他们的道德和价值观主观评判内容的好坏,并且保留权利随时将你的内容公之于众或者提交给司法机关,而且即使是脱敏了的数据也仍然可以关联到个人,且在此之上谁也说不好他们有没有拿这些数据去做别的事情

我认为这是个大问题,也是一记警钟

而且我并不觉得这只是美国之外的人应该上心的问题;任何类似的平台都可以这么做,且现在你和他们价值观相同,并不代表你们会永远相同,说不定哪天你私聊里的哪个内容就被 AI flag 了抄送党卫军

这不仅突出了数据保护法案的落实问题,打上“境外势力”标签的用户的隐私权就可以被区别对待的问题,还凸显出了本地部署模型的重要性,正好呼应了我之前分享的 blog 里的那句话:

Policy is a promise. Architecture is a guarantee.


这些服务商的隐私协议和 ZDR 里可以说的天花乱坠,但是只有跑在你本地,拔掉网线还能运行的模型输出的数据才是安全的,完全受控于你的

https://www.anthropic.com/news/detecting-and-preventing-distillation-attacks

https://openai.com/index/disrupting-malicious-ai-uses/

https://www.reddit.com/r/LocalLLaMA/comments/1rd8cfw/anthropics_recent_distillation_blog_should_make/
「第一记忆模式和第二记忆模式:Kapy 的记忆系统设计」

Kapy (short for Kapybara) 是我假期做的一个通用 agent,由于我略长于别人的假期 (thanks to dify.ai ) 就要结束了,先把 devlog 写了,精装修的 GitHub repo 之后再发。

我思考记忆系统的设计很久了,我想每一个做过 chatbot 的人应该都思考过。但我一直没有形成清晰的结论,接着这个机会逼迫自己一把,算是把我的答卷做出来了。其实做 Kapy 是我近期手写代码最多的时候,手写代码就像雕刻家一样(我想象中的雕刻家,因为我也不知道真正的雕刻家什么样),是在打磨的过程中完善思想的过程。

进入正题。这个记忆系统打一开始我就决定要做统一式的,不做基于 thread 的拆分,以原始信息作为 single source of truth。此时包括 bub 在内的 agent 已经把这条路跑通了,因此这个决策对我来说不仅是想法,是一个完全明确的方向。

统一式的架构定了,应用层总得有 compact 吧?我一直报有 turn 重要于 thread 的想法:
- 很多任务是以 turn 为单位的,比如搜索任务大概率不会有追问;
- Agent 语境下的 turn 不仅是输入-输出对,而是:输入 -> tool call loop -> 输出
- 之前在推特上我就表达过,tool call loop 不是记忆,而是工作日志。agent-human 之间的交互记忆和 tool call loop 的细节几乎没有关联。

于是 compact 的方案也自然敲定了:以一个 turn 里的 tool call loop 为最小单位做 compact,形成一个 compact node。

那记忆的基本单位就成型了:一个 memory record 对应一个 turn,包含其原始工作 log 和 compact node

那既然不要 thread,每个 turn 之间怎么串联起来呢?我立即想到了 git,也就是一个 DAG。这个形状非常合理:连边表示时序和因果,一个 memory record 上接 parents 不就构成因果链了吗?

那 parents 怎么接上呢?我试过不同方案,比如就用 thread 强制串起来?但是 agent 如果自主去查询自己的记忆,不仅限于最近的记忆了,那不也构成因果了吗?最终我认为这里大可交给 agent 自己决定:完成任务后你自己告诉我你参考了哪些过去的记忆,我帮你把这个 DAG 结构落库就好了。

很好,写入逻辑敲定了,读出呢?首先最基本的近期记忆肯定是要的,然后 agent 要自主查询它可能感兴趣的过去的记忆、包括过去的具体工作日志。这时候我已经意识到基于文件系统做事很爽,我把 memory record 的存储落在文件系统里,然后写了一个小脚本。

这个脚本有三路召回,前两路是按 thread 和 user(Kapy 会识别不同的 human user)筛选召回最近的 memory records,其中 thread 这一路自然就起到基本的最近语境上下文的作用;第三路要依赖 agent 自己传进来的 keywords 参数,按 keywords 检索过去的记忆。

这一个脚本虽然是 agent 自己调用的,但其实是半固定注入:我要求 agent 在每一个 turn 的起始第一个 tool call 必须使用这个脚本。

有了这个基础记忆,agent 至少能理解语境了。接下来,agent 或许会想起来有价值的细节需要探查:比如看完 compact 还得查一下原始日志,或者出现了新的关键词要在过去的记忆里查一查。还记得 memory records 都落在文件系统上吗?你自己用 rg sed 之类的去查吧。记得最后把 referenced memories id 告诉我就行。

至此,Kapy 的记忆系统就完成了,当然中间我也或多或少地调整了设计,总之十数天的使用下来证明它 work 的非常好。

总而言之,这个系统的原则在于两种记忆模式的并存:一是固定式的注入的记忆,这个记忆是宽泛的,大体的,把握全局的,以 compact 信息为主的;二是 agent 自主的记忆查询,这个记忆是具体的、有明确目标的, agent 知道自己在寻找什么。

实现细节上,目前自然有点粗糙,但总之要符合上述两种模式:
- 对第一个模式要提供一个高级的 API,让 agent 从零上下文的状态下就搞明白我是谁我在哪我要干什么。这个高级 API 的参数要尽量少,能写死的就写死,调用也是强制或半强制的;
- 对第二个模式则要提供一个低级的 API。Agent 此时已经明确知道自己想要什么信息,要给它尽可能大的灵活性去找到它要的信息。

比如 Kapy 的第一记忆模式目前是三路检索,前面提到的 DAG 因果链还没用上呢;第二记忆模式基于文件系统,虽然够低级,但 rg 毕竟只是基于关键字,要是加上语义检索全文检索的能力,总归能给它多两只手。

说到这里其实可以引出一个新的问题:第二记忆模式、知识库、skills,都是 agent 利用一个工具从外部去查询,它们之间是什么关系,有什么区别,是统一的同一件东西吗?还是应该区分,有不同的索引结构?我也还没想好,留作后话。

( Nowledge Mem 从记忆的方法论的角度做了一些工作,我觉得很有价值)
一篇新的文章,希望可以帮大家了解从 coding 到生活,从 coding agent 到 openclaw 或者 bub ,背后的问题、范式和模型的一些变化

https://psiace.me/zh/posts/carpenter-hammer-nail/
Back to Top