Skip to content

RAG 检索模式篇

目标:让集成方用 POST /v1/rag/retrieve 按查询文本召回当前用户有权访问的内容片段(chunk),理解返回的回链坐标(sourceDocId / sourceVersion / span)与相关性分语义,按容器缩窄检索范围,规避授权与时效相关的常见坑,进而在自己的应用里组装 RAG(检索增强生成)流程。

不在本篇范围:关键词全文搜索(按文档为粒度返回命中,见全文搜索模式篇);认证形态与委派头(见认证与身份双通道);错误码完整码表(见错误码参考)。

全文搜索回答「哪些文档与关键词相关」,RAG 检索回答「哪些内容片段与这句话语义相关」——后者返回带定位坐标的正文片段,专为「检索增强生成」类应用设计:把召回的片段作为上下文喂给大模型,并凭坐标回链原文出处。两者独立授权、互不替代。

关键事实

  • 端点:POST /v1/rag/retrieve,所需 scope:client:rag:retrieve——与全文搜索(client:search:read独立授权,默认不预授任何客户端,需在开通时显式授予。
  • ⚠️ 必须代表用户调用(强通道或弱通道),不支持 APP_ONLY。无用户身份的请求返回 HTTP 403。片段级权限过滤按当前用户执行:结果只含该用户有权读取的内容,集成方无需再做权限裁剪。
  • 检索语料来自已发布版本:文档发布后,其内容片段经异步处理就绪方可被召回(最终一致);未发布 / 草稿内容不会出现在结果中。
  • query 必填;topK 默认 10、取值范围 [1, 100],超出范围直接拒绝(不静默截断);containerId 可选,传入则只在该容器范围内召回。
  • 结果按相关性降序排列;score 仅用于本次结果内的相对比较,不同查询之间不可比,也不建议设固定阈值过滤。

一、最小调用

bash
curl -X POST 'https://api.atkonbase.example.com/v1/rag/retrieve' \
  -H 'Authorization: Bearer ${accessToken}' \
  -H 'X-Atk-User-Token: ${userToken}' \
  -H 'Content-Type: application/json' \
  -d '{
    "query": "合同到期后多久内可以续签",
    "topK": 5
  }'

期望响应(关键字段)

json
{
  "code": 0,
  "data": [
    {
      "chunkId": "CH1000042",
      "sourceDocId": "D1000001",
      "sourceVersion": "V1000003",
      "span": "{\"unit\":\"char\",\"start\":1200,\"end\":1456}",
      "text": "……合同期满前 30 日内,乙方可书面提出续签申请……",
      "score": 0.87
    }
  ]
}
字段含义
chunkId命中片段的业务键
sourceDocId源文档 ID——V1 文档端点直接可用,凭此回链原文
sourceVersion命中时锚定的源版本 ID(= 该文档当前已发布版本);引用展示时建议带上,避免文档再发版后出处错位
span定位坐标,JSON 字符串:unit 标识坐标体系,start / end 给出片段在源内容中的区间(按源内容格式可能附带页码等扩展键)。用于在原文中精确定位高亮
text片段正文——直接作为 RAG 上下文喂给生成模型
score相关性分,越大越相关;仅供本次结果内排序参考

二、按容器缩窄范围

知识库类场景常按业务域分容器存放内容,检索时传 containerId 限定范围:

bash
curl -X POST 'https://api.atkonbase.example.com/v1/rag/retrieve' \
  -H 'Authorization: Bearer ${accessToken}' \
  -H 'X-Atk-User-Token: ${userToken}' \
  -H 'Content-Type: application/json' \
  -d '{
    "query": "报销单据需要哪些附件",
    "topK": 10,
    "containerId": "${financeKbContainerId}"
  }'

范围参数只接受 containerId(闭集),不提供开放的过滤表达式;需要按字段值精确筛选文档时用元数据筛选,两者解决不同问题。

三、组装 RAG 流程(建议形态)

  1. 召回:以最终用户身份调用 /v1/rag/retrieve(强通道带 X-Atk-User-Token,或弱通道 act-as),拿 topK 片段。
  2. 拼上下文:将 text 拼入提示词;保留每条的 sourceDocId / sourceVersion / span 作为引用元信息。
  3. 生成与引用:生成模型答复后,按引用元信息渲染「出处」链接——跳转你应用内该文档的详情 / 预览页,凭 span 高亮原文位置。
  4. 空结果处理:召回为空时(无相关内容或用户无权访问任何相关内容),提示词侧应明确「未检索到资料」,避免模型凭空作答。

常见坑

  • ⚠️ 拿 APP_ONLY 身份调用:返回 HTTP 403。RAG 召回的权限过滤以用户为单位,服务端到服务端的批处理场景也必须以弱通道(act-as)指明代表的用户。
  • ⚠️ scope 漏授权client:rag:retrieve 默认不预授,未授权时返回 Scope 不足错误码(102002)。开通时与 client:search:read 分别申请。
  • ⚠️ 刚发布就检索:片段处理是发布后异步进行的,立即检索可能召不回新内容。批量灌库后建议留出处理时间,再做验证性检索。
  • ⚠️ 跨查询比较 score 或设固定阈值:相关性分只在单次结果内有序,不同查询、不同时期的分值不可比;按名次(topK)截取,不要按分值硬过滤。
  • ⚠️ 用户搜不到「自己刚上传」的内容:先确认文档已发布(草稿不入语料),再确认该用户对文档有读权限。
  • ⚠️ topK 传大于 100:直接报错拒绝,不会静默截断到 100。

下一步