RAG Pipeline 监控与重试:检索失败不是静默跳过,而是触发备选路径

📅 2026/7/7 10:51:32 👁️ 阅读次数 📝 编程学习
RAG Pipeline 监控与重试:检索失败不是静默跳过,而是触发备选路径

RAG Pipeline 监控与重试:检索失败不是静默跳过,而是触发备选路径

一、RAG 系统最常被忽略的环节是检索失败处理

RAG 架构的讨论通常聚焦在向量数据库选择、分块策略和 Embedding 模型对比上。但在生产环境里,更频繁的问题是检索失败。向量库超时、相似度阈值过高导致空结果、索引写入延迟导致新数据无法即时检索——这些情况远比"检索到了但不准"更常见。

多数 RAG 实现遇到检索失败时,会静默跳过检索结果,直接让模型用自身知识回答。这等于退回到了纯生成模式,用户完全不知道回答没有经过事实支撑。正确做法是触发备选路径,并在回答中标注信息来源状态。

二、RAG 调用链路要有显式降级和来源标注

完整的 RAG 链路应该包含检索、降级判断、模型调用和来源标注四个环节。每个环节的失败都要被记录和传递,不能被吞掉。

flowchart TD A[用户查询] --> B[查询预处理与意图分类] B --> C[向量检索] C --> D{检索结果数量} D -->|≥3条| E[正常RAG生成] D -->|1-2条| F[弱支撑RAG:标注低置信度] D -->|0条| G[触发备选路径] G --> H[关键词检索备选] H --> I{备选是否成功} I -->|是| J[备选RAG生成:标注检索降级] I -->|否| K[纯生成模式:标注无事实支撑] E --> L[回答与来源标注] F --> L J --> L K --> L

来源标注是关键。用户看到"此回答基于3条检索结果"和"此回答未经事实检索"时,对回答的信任度判断完全不同。标注不是削弱产品,而是增加透明度。

三、检索失败的重试与降级逻辑

type RetrievalResult = { chunks: string[]; scores: number[]; source: "vector" | "keyword" | "none"; latencyMs: number; }; const SIMILARITY_THRESHOLD = 0.72; const MAX_RETRIES = 2; export async function retrieveWithFallback(query: string): Promise<RetrievalResult> { // 第一次向量检索,含超时保护 for (let attempt = 0; attempt < MAX_RETRIES; attempt++) { try { const result = await vectorSearch(query, { timeoutMs: 3000 }); const filtered = result.filter((r) => r.score >= SIMILARITY_THRESHOLD); if (filtered.length >= 3) { return { chunks: filtered.map((r) => r.text), scores: filtered.map((r) => r.score), source: "vector", latencyMs: result[0]?.latencyMs ?? 0, }; } // 结果不足3条但不为空,标记为弱支撑 if (filtered.length > 0) { return { chunks: filtered.map((r) => r.text), scores: filtered.map((r) => r.score), source: "vector", latencyMs: result[0]?.latencyMs ?? 0, }; } } catch (error) { console.error(`向量检索第${attempt + 1}次失败:`, error); } } // 降级到关键词检索 try { const keywordResult = await keywordSearch(query); if (keywordResult.length > 0) { return { chunks: keywordResult, scores: keywordResult.map(() => 0.5), source: "keyword", latencyMs: 0, }; } } catch (error) { console.error("关键词检索也失败:", error); } // 全部失败,标记无检索支撑 return { chunks: [], scores: [], source: "none", latencyMs: 0 }; }

这段代码实现了向量检索重试、关键词检索降级和最终无支撑标记的完整链路。每次检索的来源和耗时都被记录,方便后续分析检索质量。

四、重试和降级不能无限制延长响应时间

RAG 系统的响应时间直接影响用户体验。两次向量检索重试加一次关键词降级,总耗时可能超过10秒。生活工具的场景下,用户对等待的容忍度更低。

合理的做法是设置总超时上限。比如整个检索环节不超过5秒,超过后直接降级到纯生成模式。宁可标注"未经事实检索",也不要让用户等太久。响应速度和信息质量需要权衡,生活应用里速度的权重往往更高。

重试次数也要克制。向量库如果是持续故障,两次重试不会有不同结果。更好的做法是把检索失败记录到监控系统,触发告警后由运维层面修复,而不是让每次请求都重复失败的检索。

五、总结

RAG Pipeline 应对检索失败做显式降级处理,不能静默跳过。链路包含向量检索重试、关键词检索备选和纯生成降级,每一步都标注来源状态。总超时不超过5秒,超过后直接标注无检索支撑。检索失败要记录到监控系统,由运维层面解决持续故障。用户看到来源标注后才能准确判断回答可信度。