【踩坑复盘】我在本地跑 RAG 知识库时踩了 5 个大坑,吐血整理避坑指南

前言

大家好,我是去年开始研究 RAG 的后端开发。

本地跑通一个 RAG 知识库听着简单------不就是"文档切分 → 向量化 → 检索 → LLM 生成"吗?但真正动手时,各种奇奇怪怪的坑一个接一个。

花了 2 周踩坑,终于把系统跑通了。 这篇文章把我踩过的 5 个大坑整理出来,避免大家再走弯路。


坑 1:LM Studio API Token 被坑了一整天 🔥

调用 http://localhost:1234/api/v1/chat 时,开始完全不报错------能正常返回。后来突然开始报:

css 复制代码
An LM Studio API token is required to make requests to this server,
but none was provided using the Authorization header

我以为 Token 过期了,重启 LM Studio、重新生成 Token,还是一样。

最后发现:LM Studio 有两套 API!

API 类型 端点 Token
Local Server API /v1/chat/completions ✅ 需要 Bearer Token
Developer API /api/v1/chat 部分版本免 Token
java 复制代码
// ✅ 正确:Local Server API + Bearer Token
String url = lmstudioUrl + "/v1/chat/completions";

Request request = new Request.Builder()
    .url(url)
    .addHeader("Authorization", "Bearer " + apiKey)  // 关键!
    .addHeader("Content-Type", "application/json")
    .post(RequestBody.create(jsonBody, MediaType.parse("application/json")))
    .build();

// ❌ 错误:Developer API 免 Token 的写法,不通用
String url = lmstudioUrl + "/api/v1/chat";

关键点:看清楚你调的是哪套 API,Token 策略完全不同!


坑 2:Embedding 向量维度不匹配,Qdrant 存储报错 🔥

向量化存储时报错:

vbnet 复制代码
Response: BadRequest:{"status":{"error":"Wrong vector dimension...

我的 Embedding 模型是 text-embedding-bge-base-zh-v1.5,理论上输出 768 维向量。但 Qdrant 创建 Collection 时,我用了默认维度 1024。

先测一次向量维度:

json 复制代码
curl http://localhost:1234/v1/embeddings \
  -H "Authorization: Bearer $LM_API_TOKEN" \
  -d '{"model":"text-embedding-bge-base-zh-v1.5","input":["测试文本"]}'

返回结果里数组长度就是真实维度。

创建 Qdrant Collection 时指定正确维度:

scss 复制代码
// ✅ 正确
qdrantClient.createCollection(
    CollectionName,
    VectorParams.builder()
        .size(768)  // 和 Embedding 模型输出维度一致!
        .distance(Distance.Cosine)
        .build()
);

// ❌ 错误:用错了维度
.size(1024)  // 导致存储失败

避坑建议: 把向量维度写成配置项:

yaml 复制代码
# application.yml
qdrant:
  vector-dimension: 768

坑 3:文本切分把句子拦腰截断,回答质量断崖式下降 🔥

早期用的是纯长度切分:

arduino 复制代码
// ❌ 简单粗暴的切分------把句子拦腰截断
String chunk = text.substring(i, i + 1000);

结果:检索出来的片段经常是半截句子,LLM 完全无法理解。

比如切到"公司成立于 201"------LLM 根本不知道后面是什么。

scss 复制代码
public List<String> chunkText(String text) {
    List<String> chunks = new ArrayList<>();
    StringBuilder current = new StringBuilder();

    // ✅ 按句子边界分割(中文:。!?;\n)
    String[] sentences = text.split("(?<=[。!?.!?;;\n])");

    for (String sentence : sentences) {
        // 当前块加上这句超过阈值
        if (current.length() + sentence.length() > chunkSize) {
            // 保存当前块
            if (current.length() > 0) {
                chunks.add(current.toString().trim());
            }

            // 保留重叠部分(避免丢失上下文)
            int overlapLen = Math.min(chunkOverlap, current.length());
            current = new StringBuilder(
                    current.toString().substring(current.length() - overlapLen)
            );
        }
        current.append(sentence);
    }

    if (current.length() > 0) {
        chunks.add(current.toString().trim());
    }
    return chunks;
}

加上重叠(Overlap)效果更好:

ini 复制代码
Chunk1: [句子1][句子2][句子3]...
Chunk2: [...句子3][句子4][句子5]...  ← 重叠部分保证上下文连续

坑 4:LM Studio Embedding 接口不稳定(/v1/embeddings) 🔥

部分版本的 LM Studio,/v1/embeddings 接口返回错误:

json 复制代码
{"error": "model not found"}

但明明 v1/models 里能看到这个模型。

原因

LM Studio 对 Embedding 模型的支持比较微妙,有些 GGUF 格式的 Embedding 模型在部分版本中不稳定。

解决方案

换成 Ollama 运行 Embedding

bash 复制代码
# 安装 Ollama
winget install Ollama.Ollama

# 下载 Embedding 模型(nomic-embed-text,约 274MB)
ollama pull nomic-embed-text

# 启动
ollama serve

修改配置:

yaml 复制代码
# application.yml
ollama:
  base-url: http://localhost:1234  # 如果 LM Studio 在这里
  embeddings-model: nomic-embed-text

# 改成 Ollama:
ollama:
  base-url: http://localhost:11434
  embeddings-model: nomic-embed-text

坑 5:向量检索相似度阈值设错,噪声答案满天飞 🔥

系统上线后,经常出现"答非所问"的情况------检索出来的片段和用户问题根本不相关,但 LLM 硬是"强行回答"了。

看了日志,发现检索出来的片段相似度只有 0.1~0.2(理论上 0.5+ 才算相关),但都被塞进 Prompt 里了。

scss 复制代码
public List<SearchResult> search(String query, int topK) {
    List<SearchResult> allResults = qdrantClient.search(...);

    // ✅ 加阈值过滤:只返回相似度 >= 0.3 的结果
    return allResults.stream()
            .filter(r -> r.getScore() >= 0.3)
            .limit(topK)
            .collect(Collectors.toList());
}

不同 Embedding 模型相似度分布不同,建议先跑几个测试:

Embedding 模型 优质答案阈值
bge-base-zh-v1.5 ≥ 0.5
nomic-embed-text ≥ 0.6
text-embedding-v2 ≥ 0.55

总结一下: 5 个坑一次排雷

原因 解决
LM Studio Token 不一致 两套 API 混用 统一用 Local Server API + Bearer Token
向量维度不匹配 Qdrant 维度写错 先测试实际维度再创建 Collection
文本切分截断句子 纯长度切分 按句子边界切分 + 重叠
Embedding 接口不稳定 LM Studio 版本问题 换成 Ollama 或在线 API
噪声答案满天飞 无阈值过滤 score >= threshold 过滤

相关推荐
大模型真好玩1 小时前
LangChain DeepAgents 速通指南(九)—— 生产级智能体框架 DeepAgents Code 源码导读
人工智能·langchain·agent
用户018349301694 小时前
用Zustand管理AI多会话状态
人工智能
武子康6 小时前
调查研究-198 Agent 到底该记住什么?读懂《What Must Generalist Agents Remember?》
人工智能·openai·agent
aqi006 小时前
15天学会AI应用开发(九)利用Chroma持久化向量数据
人工智能·python·大模型·ai编程·ai应用
武子康8 小时前
调查研究-197 FAISS vs Elasticsearch 全面对比:从向量检索、全文搜索到 RAG 选型指南
人工智能·elasticsearch·agent
青禾网络8 小时前
Web 前端如何接入 AI 音效生成:从零到可用的完整方案
人工智能·设计模式
用户252736278148 小时前
【技术实战】用 Spring Boot + Vue3 + LM Studio 在本地跑通 RAG 知识库
人工智能
用户5191495848458 小时前
VBScript随机数生成器内部机制:从时间种子到密码令牌破解
人工智能·aigc