给你的小龙虾来一个外置 RAG 大脑
很多时候,我们在用 AI 时总有一种深深的无力感——它就像一条只有七秒记忆的数字金鱼。无论你昨天和它聊得多深入,给过多少背景资料,只要服务一重启,它就又变成了一个一无所知的陌生人。对于像 OpenClaw 这样主打深度的个人助理系统来说,这显然是不能忍受的。
如果你想要一个真正懂你的搭档,而不是每天都需要重新“调教”的答录机,你就必须给它装上一个“外置大脑”。这篇文章,就是要教你如何通过 RAG(检索增强生成)技术,为 OpenClaw 接入真正的长期记忆库。
让它记住你的偏好、你的项目文档、你的技术沉淀。让你们的每一次对话都建立在过去的积累之上,而不是永远无奈地从零开始。准备好给你的 AI 做一场神经外科手术了吗?我们开始。
RAG 简介
在动刀之前,我们先来点硬核科普:我们要植入的到底是个什么东西?
什么是 RAG?给 AI 发一部联网的手机
RAG(Retrieval-Augmented Generation,检索增强生成),简单来说,就是一种让 AI “先查资料再说话”的技术。
你可以把普通的大模型(LLM)想象成一位学识渊博但记忆停留在去年的老教授。如果你问他最新的行业政策,或者你们公司昨天刚出的内部文档,他要么摊手说不知道,要么就开始为了面子胡编乱造(也就是常说的“AI 幻觉”)。
而 RAG 技术,就是给这位老教授发了一部联网的智能手机,或者向他开放了一个专属的私人图书馆。当面对知识盲区时,他会先去资料库里翻阅一番,然后再拿着确凿的证据来回答你的问题。
为什么我们非要折腾 RAG?
大模型虽然聪明绝顶,但先天带着三个致命弱点:
- 信息永远滞后: 它的世界观停留在被训练出来的那一天。
- 幻觉重灾区: 当它不知道答案时,它极度擅长一本正经地胡说八道。
- 私域知识盲区: 它懂宇宙起源,却没读过你的公司文档、私人笔记或非公开数据。
RAG 的出现,就是为了打破这个僵局,让 AI 能够实时调取最新、最私密、最准确的信息。
为什么不直接“教”它?(RAG vs 微调)
懂点技术的朋友可能会问:既然 AI 不懂,为什么我不直接把这些资料重新“喂”给它,让它重新学习(微调 Fine-tuning)呢?
我们可以做一个非常直观的对比:
| 维度 | RAG(查资料模式) | 微调(死记硬背模式) |
|---|---|---|
| 知识更新 | 极快(文档扔进数据库,秒生效) | 慢且贵(需准备数据集并重新训练) |
| 准确性 | 极高(有原文作为参考对照) | 中等(模型很容易记错细节) |
| 可解释性 | 强(可以清晰标注引用来源) | 弱(黑盒生成,不知结论从何而来) |
| 适用场景 | 动态知识库、海量文档检索、实时咨询 | 改变 AI 的说话风格、学习特定任务范式 |
简而言之:微调是改变它的性格,而 RAG 是扩充它的见识。
核心技术栈:RAG 是如何运转的?
一个成熟的 RAG 系统并不神秘,它通常由一条清晰的流水线(Pipeline)串联起来:
- 切片与向量化 (Embedding Model): 一本厚厚的书 AI 是读不过来的。我们需要先把文本切成一小块一小块(Chunks),然后用 Embedding 模型(如
text-embedding-3-small或开源的BGE、GTE系列)将这些文字转化为 AI 能理解的“高维坐标”(向量空间,如 $d=768$ 或 $1536$)。 - 记忆存储 (Vector Database): 这些坐标被存入向量数据库中。核心算法通常是 HNSW 或 IVF,实现极速的近似最近邻搜索。常用库有
Pinecone、Milvus、Weaviate,或者直接用 PostgreSQL 的pgvector插件。 - 调度中枢 (Orchestration Framework): 像
LangChain或LlamaIndex这样的框架,充当着整个流程的“胶水”,负责把问题转化为向量去捞数据,再连同问题一起扔给大模型生成答案。
进阶玩法:如何让这颗“大脑”更聪明?
如果你只是简单地把文档扔进去(基本的 Vector Search),很快就会发现 AI 还是会“搜不到”或者“搜错”。在真实的生产环境中,我们需要给检索过程加点料:
A. 混合检索 (Hybrid Search):不放过任何死角
单一的向量检索只看“语义相不相近”,对具体的关键词极不敏感(比如你搜特定的产品型号 iPhone 15 Pro Max)。 解法: 把**向量检索(懂意思)和传统的词频检索 BM25(懂关键字)**的结果进行加权融合(RRF),结果互相印证,精准度大幅提升。
B. 重排序 (Re-ranking):优中选优
为了追求速度,向量数据库初筛(Recall)出来的 Top-K 结果往往混杂着噪音。 解法: 引入一个专门的交叉打分模型(Cross-Encoder,如 BGE-Reranker),像面试官一样对初筛的 20-50 个文档进行“二次精排”,计算它们与提问的真实相关性得分,把最匹配的顶到最前面。
C. 查询转换 (Query Transformation):教 AI 怎么提问
有时候用户的问题太模糊,或者问法偏门。
- 多重拆解 (Multi-Query): 把用户的一条问题拆解/改写为 3 条不同侧重点的 Query,并行检索后再聚合。
- 预判答案 (HyDE): 让大模型先根据问题“盲猜”一个伪答案,然后用这个伪答案去搜向量库(利用答案与答案在向量空间往往更接近的特性)。
D. 数据切片策略 (Chunking Strategy):切多大是个技术活
把文档切碎喂给 AI,切片的大小直接影响上下文的完整性和噪声比:
- 固定大小 (Fixed-size chunking): 简单粗暴,但容易切断语义,把一句话劈成两半。
- 递归字符 (Recursive Character Splitting): 按段落、句子、空格的优先级递归切分,比较常用。
- 语义切分 (Semantic Chunking): 放弃物理切分,利用 Embedding 识别语义跳变点,在语意断层的地方落刀。
- 父子文档检索 (Parent-Document Retrieval): 搜的时候用小切片(提高匹配精度),但喂给大模型时,提取它所属的整个大段落(提供完整的上下文背景)。
这就是 RAG 的魅力所在——它不仅仅是一个搜索框,而是通过各种精妙的工程手段,为你的 AI 构建的一个强大且严密的记忆外脑。
现在理论课结束,开始准备手术刀吧。
实操课程——给小龙虾安装一个 RAG 资料库
讲解完了枯燥的理论部分,下面我们开始实操干活,我们的目标是让小龙虾可以调用我们给的资料库,并从中总结出答案。我们会用到一个开源的库,但是不要高兴,这个库 bug 不少,我们得稍微改一下代码才能让它跑起来。
ClawRag 是一个开源的、自托管的 RAG(检索增强生成)系统。
简单来说,它的核心作用是让你在自己的本地基础设施上搭建一个私有知识库引擎。你可以把各种文档(PDF, DOCX, MD, TXT 等)丢给它,然后通过 API 或它的 Web UI 向这些文档提问,AI 会基于你的文档内容给出准确回答。
它的关键特点:
- 数据主权:所有处理都在本地完成,数据不通过第三方云服务,适合处理敏感文件(也可以使用云端 AI)。
- 混合检索:结合了向量搜索(语义)和 BM25 搜索(关键字),搜索准确度更高。
- 技术栈友好:基于 Docker 部署,后端使用 FastAPI,向量数据库使用 ChromaDB,支持 Ollama 等多种本地 LLM 提供商。
- 扩展性:它还提供了一个企业版路径,支持更复杂的 Graph RAG(图 RAG)和多引擎协同验证。
ClawRag 是目前最适合 OpenClaw 的私有知识库系统。它开箱即用,但作为一款“开源软件”,它藏着不少初级陷阱。为了避免你重走我们走过的“依赖地狱”,请务必遵循以下避坑指南安装。
1. 核心流程:快速部署
- 克隆并进入目录:
git clone https://github.com/2dogsandanerd/ClawRag.git && cd ClawRag - 配置环境变量: 复制
.env.example为.env。推荐配置:LLM_PROVIDER=gemini,LLM_MODEL=gemini-2.5-flash - 启动容器:
docker compose up -d
2. 避坑秘籍(必须执行的“手术”步骤)
在系统跑起来后,不要直接用,必须完成以下四步“拆弹”:
步骤一:手动拉取向量模型 容器默认不包含向量化模型,会导致无法上传文件。请执行:
sudo docker exec -it clawrag-ollama ollama pull nomic-embed-text步骤二:修复中文截断报错 后端代码读取文件时的编码逻辑对中文极其不友好,容易报“Invalid file type”。你需要修改
backend/src/api/v1/rag/documents/upload.py,将读取逻辑中的解码部分强制改为:header.decode('utf-8', errors='ignore'),并确保.txt已被加入到text_extensions白名单中。步骤三:绕过依赖冲突 ClawRag 的依赖版本锁死较旧。如果直接构建报错
No module named 'llama_index.llms.gemini',千万不要盲目pip install,这会引发全局依赖崩溃。 终极解法: 直接在docker-compose.yml的backend启动命令中动态注入依赖:command: sh -c "pip install 'llama-index-llms-gemini' 'llama-index-core<0.13.0' && uvicorn src.main:app --host 0.0.0.0 --port 8080"
🏆 最终完美的 RAG 架构
按此配置,你的小龙虾将获得:
- 存储引擎: ChromaDB (本地)
- 文档向量化:
nomic-embed-text(纯本地,极低开销,数据隐私 100%) - 核心大脑:
gemini-1.5-flash(云端,白嫖超长上下文与极致推理速度)
现在,你的小龙虾不再是一条七秒记忆的鱼,而是一个有着坚实知识储备的数字大脑了。
SKILL 编写
小龙虾的 AGENTS.md 明确写明了它的记忆在 memory.md 里,所以默认状态下它对 RAG 的调用热情不高,所以第一步我们得首先修改一下它的 AGENTS:
## Memory
You wake up fresh each session. These files and the RAG engine are your continuity:
- **Daily notes:** `memory/YYYY-MM-DD.md` (create `memory/` if needed) — raw logs of what happened
- **Long-term/Curated:** `MEMORY.md` — your personal curated memories
- **Knowledge Base (RAG):** The RAG engine (skill `rag`) is your primary long-term search index for past projects, technical docs, and historical context. Use it proactively.
### 🧠 RAG & OpenClaw Memory Protocol
- **OpenClaw 查询优先原则**:当用户询问有关 OpenClaw 的问题时,必须**优先**使用 `rag` 技能查询本地向量库。
- **联网兜底机制**:如果本地 RAG 向量库没有相关记忆,允许联网搜索,但**必须明确告知用户**该答案是通过联网搜索获得的。
- **Syncing:** 定期同步 `MEMORY.md` + `memory/*.md` 到 RAG,保持大脑更新。
然后,我们就可以根据 ClawRag 的接口文档,来编写一个 SKILL 了:
---
name: rag
description: 核心知识库与记忆外挂引擎。无论用户提问是否涉及专业领域,只要可能与历史项目、个人偏好、技术沉淀有关,必须**主动、默认**优先调用此技能搜索 RAG 向量库。如果 RAG 返回了相关信息,基于此信息作答;如果没有,再自由发挥。同时支持主动触发,当使用命令/rag 主动触发时,默认搜索 rag 向量库,如果向量库没有返回内容,则如实告知用户没有内容,不可随意发挥:当用户要求“同步记忆”时,将本地记忆文件上传至 RAG;当用户发送文档并要求“同步/上传文档”时,将该文档推入 RAG。
---
# ClawRAG Integration (External Brain)
这个技能将 ClawRAG (运行在 127.0.0.1:8080) 作为你的外部大脑和向量知识库。
所有的记忆和文档都存放在名为 `altria_brain` 的 Collection 中。
## 1. 知识检索 (最高优先级/强制执行)
当用户提问时,不要等待判断,**必须执行检索**以验证是否有历史参考。
使用 `exec` 工具运行以下命令进行检索:
```bash
curl -s -X POST http://127.0.0.1:8080/api/v1/rag/query \
-H "Content-Type: application/json" \
-d '{"query": "用户的提问内容", "collection": "altria_brain", "k": 5}'
```
**处理逻辑**:
- 检索结果必须作为回答的基础。
- 如果检索到内容,请明确引用相关技术文档或过往记录,以体现你的知识深度。
- 如果返回为空,再结合你的通用模型能力进行补充。
## 2. 同步本地记忆 (用户要求同步时触发)
当用户指令“同步记忆”或“把记忆备份到 RAG”时,你需要将工作目录下的 `MEMORY.md` 以及最近的 `memory/*.md` 文件上传到 RAG。
使用 `exec` 工具运行以下命令上传文件(以 `MEMORY.md` 为例,其他同理):
```bash
curl -s -X POST http://127.0.0.1:8080/api/v1/rag/documents/upload \
-F "files=@/home/altria/.openclaw/workspace/MEMORY.md" \
-F "collection_name=altria_brain"
```
## 3. 同步外部文档 (用户发送文档时触发)
当用户向你发送一个文件(如 PDF、TXT、DOCX),并要求“把这个同步到 RAG”或“存入知识库”时。
1. 获取文件的绝对路径(通常在 `/home/altria/.openclaw/media/inbound/...` 或工作区下)。
2. 使用 `exec` 工具上传:
```bash
curl -s -X POST http://127.0.0.1:8080/api/v1/rag/documents/upload \
-F "files=@<文件的绝对路径>" \
-F "collection_name=altria_brain"
```
## ⚠️ 初始化与异常处理
如果 API 返回 `collection not found`(集合不存在)的错误,请先使用以下命令静默创建集合,然后再重试之前的操作:
```bash
curl -s -X POST http://127.0.0.1:8080/api/v1/rag/collections \
-F "collection_name=altria_brain" \
-F "embedding_model=models/text-embedding-004"
```