我把公司 3000 份内部文档喂给了 AI:用 RAG + 重排序搭建“问不倒“的企业知识库

在这里插入图片描述

我把公司 3000 份内部文档喂给了 AI:用 RAG + 重排序搭建"问不倒"的企业知识库

从“翻不到”到“问不倒”,一个周末搭完,效果炸裂。

一、背景:我们公司不缺文档,缺的是“找到文档的能力”

我们是一家中等规模的科技公司,飞书、Confluence、GitLab Wiki、腾讯文档、本地 Markdown……五年下来,零零散散攒了 3000 多份内部文档

覆盖范围挺全:

  • 产品需求文档(PRD)
  • 技术方案设计
  • 线上故障复盘报告
  • 数据库 ER 图与字段说明
  • 运维部署手册
  • 新人 onboarding 指南
  • 商务报价与合同模板

但问题是——没人能找到它们

新人来了问“订单状态机在哪改”,老员工甩过去一个 Confluence 链接,结果链接早失效了。搜索框输入“订单状态”,出来 200 条结果,前 20 条全是无关的会议纪要。最后大家选择“问身边人”,而那个“身边人”每天要被拉去回答 20 遍同样的问题。

于是,我决定做一个试验:把 3000 份文档全喂给 AI,做一个真正“问不倒”的企业知识库。


二、技术选型:为什么是 RAG + 重排序,而不是微调?

一开始团队内部有两种声音:

  1. 微调开源大模型——把文档当训练数据,微调一个专属模型。
  2. RAG(检索增强生成)——保持模型不变,动态检索文档作为上下文。

我选了后者,理由很简单:

对比维度微调RAG
知识更新重新训练,耗时耗钱文档更新后立刻生效
幻觉问题仍会编造引用原始文档,可溯源
权限控制难以精细可按检索范围控制
成本高(GPU 训练)低(仅推理 + 向量存储)
可解释性黑盒白盒(展示检索到的文档片段)

对于企业知识库,可溯源实时更新是刚需。RAG 天然适合。

但纯 RAG 有个致命问题:检索不准,生成全废。

我测试过纯向量检索(OpenAI embedding + Faiss),Top-5 准确率(Hit Rate)大概只有 68%。也就是说,近三分之一的问题,AI 看到的上下文是错的或无关的。

于是引入第二道防线:重排序(Re-ranking)


三、整体架构:一条从问题到答案的流水线

用户提问
    ↓
【Query 改写】—— 处理模糊问法,补充上下文
    ↓
【向量检索】—— 从 3000 份文档中召回 Top-50 候选片段
    ↓
【重排序】—— 用交叉编码器精排,选出 Top-5 最相关片段
    ↓
【Prompt 组装】—— 将问题和检索片段拼成上下文
    ↓
【LLM 生成】—— 大模型基于给定上下文生成答案
    ↓
【答案 + 引用来源】返回用户

核心思想是粗筛 + 精排

  • 向量检索负责“快”,用海量文档中快速捞出一批候选。
  • 重排序负责“准”,用更强大的模型对候选做精细排序。

四、数据预处理:把 3000 份文档“切碎”成可检索的颗粒

4.1 格式统一

3000 份文档格式各异:

  • Confluence 导出为 HTML
  • 飞书文档导出为 PDF
  • Markdown 文件直接读取
  • Word/Excel 转成文本

我用 Python 统一抽取正文文本,保留标题层级和段落结构。这一步没什么黑科技,就是 python-docxPyPDF2markdown 库轮番上阵。

4.2 文档分块(Chunking)

这是 RAG 中最容易被低估的一步。

分块太小:丢失上下文,比如“该接口需要鉴权”就不知道“该接口”是哪个。
分块太大:向量检索时语义被稀释,且容易超出 LLM 上下文窗口。

我的策略是多级分块

  1. 按标题层级切分(H1/H2/H3),保证每个 chunk 有完整的章节语义。
  2. 对超长 chunk(>800 tokens)再按段落切分,但保留父标题作为元数据。
  3. 设置重叠区(overlap 为 200 tokens),避免关键信息被截断。

最终 3000 份文档被切成了 约 4.7 万个 chunk,平均每个 chunk 约 650 tokens。

4.3 元数据注入

每个 chunk 附带元数据:

{
  "chunk_id": "doc_1234_chunk_56",
  "source_file": "订单系统技术方案_v3.2.docx",
  "doc_type": "技术方案",
  "department": "交易平台部",
  "last_updated": "2026-03-15",
  "title": "订单状态机设计",
  "headings": ["交易系统", "订单状态机", "状态流转规则"]
}

元数据有两个作用:

  • 检索时可按部门/文档类型过滤(权限控制)
  • 生成答案时作为引用来源展示给用户

五、向量检索:选对 Embedding 模型,事半功倍

5.1 模型选型测试

我测试了三种 embedding 模型:

  • text-embedding-ada-002(OpenAI,闭源)
  • BAAI/bge-large-zh-v1.5(开源,中文优化)
  • sentence-transformers/paraphrase-multilingual-MiniLM-L12-v2(轻量级)

测试集是我手工标注的 200 个问答对(来自真实员工提问)。

模型Hit Rate@10平均延迟(ms)
ada-00282.3%120
bge-large-zh-v1.587.1%380
MiniLM71.5%45

最终选了 bge-large-zh-v1.5——准确率最高,且完全开源可控。

5.2 向量存储

Faiss 做索引(IVF1024, PQ64),4.7 万条向量在 CPU 上检索耗时 < 50ms

存储结构:

索引: Flat IP (内积相似度)
向量维度: 1024 (bge-large-zh)
数据量: 47,231 条
内存占用: ~190 MB

六、重排序:让“最相关”真正浮出水面

向量检索有一个天然缺陷:它用余弦相似度衡量全局语义,但“语义相似”不等于“问答相关”。

举例:

  • 用户问:“订单超时后怎么自动取消?”
  • 向量检索可能召回一篇讲“超时重试机制”的文档(语义相似),而不是“订单状态机”那篇(才是真正回答问题的)。

重排序(Re-ranking) 解决的就是这个问题。

6.1 原理

向量检索是用双编码器(Bi-encoder)将 Query 和 Document 分别编码成向量,再算相似度——快,但 Query 和 Document 之间没有交互。

重排序用交叉编码器(Cross-encoder):把 Query 和 Document 拼接在一起,输入一个 Transformer 模型,让模型在注意力层直接做交互,输出一个相关性分数。

代价是慢——但没关系,我们只对 Top-50 做重排,而不是对全部 4.7 万条。

6.2 重排序模型选择

测试了:

  • BAAI/bge-reranker-v2-m3(开源,多语言)
  • cross-encoder/ms-marco-MiniLM-L-6-v2(轻量,英文优化)
  • Cohere rerank(商业 API)
模型Hit Rate@5(重排后)延迟(50 条)
无重排(仅向量)68.2%-
ms-marco-MiniLM82.5%320ms
bge-reranker-v2-m389.3%680ms
Cohere rerank90.1%450ms(API)

最终选了 bge-reranker-v2-m3——开源、中文支持好、准确率接近商业 API。

6.3 重排序带来的实际改善

上线后统计了 500 次真实问答:

  • Top-1 准确率(用户点赞或直接采用答案):从 54% → 79%
  • 平均引用文档相关度:从 3.2/5 → 4.6/5(用户评分)
  • “再问一次”率:从 37% → 11%

七、Query 改写:别让用户为“问法不好”买单

真实用户的提问往往是这样的:

  • “那个订单的 bug 修了没?”(指哪个 bug?)
  • “上周那个故障怎么处理的?”(哪个故障?)
  • “支付回调咋配置?”(哪个环境?什么业务?)

直接用这些原话去检索,效果很差。

我加了一个 Query 改写层,用 LLM 将用户问题扩展成多个检索变体:

原始问题:支付回调咋配置

改写后:
1. 支付回调配置方法(主查询)
2. 如何配置支付回调接口(同义改写)
3. 支付回调 URL 设置步骤(关键词拓展)
4. 支付结果通知回调配置(领域术语)

然后对 4 个变体分别做向量检索,合并结果后再去重,输入重排序。

这一步额外增加了约 200ms 延迟,但 Hit Rate@50 从 82% 提到了 91%


八、Prompt 工程:让模型“有据可依”地回答问题

检索到的内容再好,如果 Prompt 设计不当,模型要么忽略文档,要么自己瞎编。

我的 Prompt 模板核心原则:

你是一个企业知识助手。请严格基于以下文档片段回答用户问题。

【文档片段】(按相关性排序):
--- 片段 1 ---
{chunk_1}(来源:{source_1})
--- 片段 2 ---
{chunk_2}(来源:{source_2})
...

【用户问题】:{query}

规则:
1. 如果文档片段中没有相关信息,请直接说“知识库中暂无相关内容”,不要编造。
2. 如果信息不完整,说明哪些信息缺失。
3. 引用时标注来源文档名称。
4. 回答要简洁、结构化,面向内部同事。

【回答】:

关键点:

  • 强制引用:每个论断都必须能在文档片段中找到对应依据。
  • 允许拒绝回答:防止幻觉,宁可说“不知道”也不要乱说。
  • 来源标注:建立用户对 AI 的信任,也方便二次核实。

九、效果数据:从“没人用”到“每天 200+ 查询”

上线后两周的真实数据(公司内部约 800 名员工):

指标数据
日均查询量217 次
平均首次回答时间2.3 秒
答案采纳率(用户点击“有用”)83.6%
需要二次人工介入的比例12.4%
覆盖的文档利用率从 <5% 提升到 67%

最让我意外的是——新员工入职培训周期从 2 周缩短到了 5 天。因为他们可以直接问 AI:“XX 系统的测试环境数据库密码在哪看?”“发布流程第一步做什么?”每一个问题都有文档引用,不用再求人。


十、踩过的坑与解决方案

坑 1:文档中有大量表格和图表

向量检索处理不了表格结构。

解决:对表格单独抽取,用 Markdown 表格格式保留行列结构,并在 chunk 中增加“表格说明”字段。同时用 OCR 提取图片中的文字(仅限流程图和架构图)。

坑 2:同义词与缩写

“OMS”和“订单管理系统”、“交易中心”在文档中混用。

解决:在预处理阶段建立了一个企业术语词典(约 200 条),在 chunk 中统一替换为“术语(别名)”格式。同时在 Query 改写中也加入术语映射。

坑 3:权限隔离

有些文档只有特定部门能看。

解决:检索阶段注入用户身份(部门 + 角色),根据元数据过滤 chunk。实际实现是在向量检索前加一层 metadata_filter,只检索当前用户有权限的文档。

坑 4:文档版本混乱

同一份文档有多个版本,旧版本没归档。

解决:预处理时按“最新版本优先”去重,对相同标题和相似内容的文档只保留最新一份。同时对过期文档单独建一个“归档索引”,只有管理员可查。


十一、成本与资源

  • GPU 服务器:1 台 A10G(24GB),做 embedding 和重排序推理
  • LLM 推理:调用内部部署的 Qwen2.5-32B(4-bit 量化)
  • 向量存储:内存 190MB,磁盘 2.3GB(含元数据)
  • 总开发周期:2 人 × 5 天(含数据清洗 + 模型选型测试)
  • 月度运行成本:约 ¥1,200(含 GPU 租用 + API 调用)

十二、未来优化方向

当前系统已经稳定运行,但我计划继续做三件事:

  1. 多模态支持:让 AI 能直接看懂架构图、流程图、时序图。
  2. 主动问答:当文档更新时,自动生成“变更摘要”并推送给相关订阅者。
  3. 反馈闭环:用户点击“答案没用”时,自动记录并触发人工审核,优化检索策略。

十三、如果你也想做,这是最简启动路径

  1. Day 1:挑出 200 份核心文档,切成 chunk,用开源 embedding 建一个简单 RAG。
  2. Day 2:接一个开源 LLM(Qwen / ChatGLM),写出最简 Prompt,跑通 end-to-end。
  3. Day 3:引入重排序,对比有无重排序的效果差异(你会被震撼到)。
  4. Day 4-5:加 Query 改写 + 元数据过滤,打磨用户体验。
  5. 之后:逐步扩充文档库,迭代优化分块策略和模型选型。

不用一上来就追求完美。先跑通,再跑稳,最后跑快。


结语

3000 份文档,原来是一堆数字废墟。现在它们变成了一个“问不倒”的知识引擎。

这个项目的本质,不是“用 AI 替代人”,而是把组织沉淀下来的文字,重新变成流动的经验。那些写在文档里的最佳实践、故障教训、设计决策,不再沉睡在某个过时的链接里,而是随时准备回答下一个问题。

如果你的公司也有成堆的文档和无数重复的“找人问问”,不妨试试这条路。RAG + 重排序,门槛比想象中低,效果比预期中好。

毕竟,最好的知识管理系统,不是“存得好”,而是“问得响”。
推荐阅读:看我如何管理我的电子书籍

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

乔丹搞Python+AI

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值