Files
ai-contract-platform/project-docs/V2-rag-search-explain-enhancement-2026-06-24.md
T
yuqei a3bb78e06b
Security Quality Gate / npm audit, Bandit, pip-audit, detect-secrets (pull_request) Failing after 16m35s
release: freeze V2 release candidate
2026-07-12 15:32:24 +08:00

208 lines
5.2 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# AI 合同平台 V2:RAG 检索 Explain 增强
日期:2026-06-24
## 本轮目标
在完成 pgvector HNSW 和关键词 `search_vector` SQL 优化后,本轮补齐 RAG 检索可解释性:
- 说明一次检索是否使用 HNSW。
- 说明一次检索是否使用 `search_vector`。
- 返回向量候选数、关键词候选数、融合去重后的候选数。
- 给每条候选返回来源和排序原因,帮助管理员判断“为什么命中这条依据”。
这属于 AI 中台能力,不把检索细节塞回合同系统,仍符合 V2 重构方案中“合同系统只做业务、AI 中台负责模型/知识库/RAG/审计”的边界。
## 已完成代码
文件:
- `yuqei-ai-platform/services/ai-platform-api/src/yuqei_ai_platform_api/repository.py`
- `yuqei-ai-platform/services/ai-platform-api/tests/test_platform_data.py`
### 1. Explain 响应新增字段
`KnowledgeSearchExplain` 新增:
- `vector_backend`
- `keyword_backend`
- `used_hnsw`
- `used_search_vector`
- `vector_candidate_count`
- `keyword_candidate_count`
- `merged_candidate_count`
`KnowledgeSearchExplainItem` 新增:
- `candidate_source`
- `ranking_reason`
### 2. PostgreSQL explain 走真实检索路径
SQLAlchemy/PostgreSQL 仓库的 explain 不再只用“最近 N 条内存候选”模拟,而是按策略走真实数据库路径:
- `hybrid`:
- pgvector HNSW 取向量候选
- `search_vector @@ plainto_tsquery(...)` 取关键词候选
- 合并去重后计算关键词分、向量分、混合分
- `vector`:
- 只走 pgvector HNSW
- 与正式搜索保持一致:即使低于阈值,也解释 top vector 候选
- `keyword`:
- 只走 `search_vector`
### 3. 排序原因
每条结果返回类似:
```text
hybrid score 0.6326 = keyword 1.0000 * 0.55 + vector 0.1835 * 0.45; source=vector; matched_terms=押金
```
或:
```text
vector score 0.2293; source=vector
```
或:
```text
keyword score 1.0000; source=keyword; matched_terms=租赁
```
这样管理员可以直接看到命中来源、分数构成和匹配词。
## 本地验证
命令:
```powershell
python -m pytest yuqei-ai-platform\services\ai-platform-api\tests -q
python -m compileall yuqei-ai-platform\services\ai-platform-api\src\yuqei_ai_platform_api\repository.py
```
结果:
- `41 passed`
- compileall 通过
新增/更新测试:
- 内存 explain 仍返回基础字段,兼容原 explain 行为。
- explain 模型可以表达 `postgres-pgvector`、`pgvector-hnsw`、`search_vector`、候选数和排序原因。
## V2 smoke 部署验证
部署命令:
```powershell
$env:SSHPASS='YOUR_REMOTE_PASSWORD'
powershell.exe -NoProfile -ExecutionPolicy Bypass -File yuqei-infra\scripts\deploy-v2-smoke-docker.ps1 -UseSshpass -AllowDirtyWorktree -SkipSmoke
```
最终结果:
- `V2_SMOKE_DOCKER_DEPLOY_PASS`
- 产物目录:`project-docs/qa-artifacts/v2-smoke-docker-deploy/2026-06-24T21-53-40`
中间情况:
- 第一次部署失败原因仍是 Docker 镜像代理 TLS 超时,不是代码问题。
- 重跑后部署通过。
## 远端接口抽样
接口:
```http
GET /api/v1/knowledge-chunks/search/explain
```
### hybrid:押金
结果摘要:
```json
{
"retrieval_backend": "postgres-pgvector",
"vector_backend": "pgvector-hnsw",
"keyword_backend": "search_vector",
"used_hnsw": true,
"used_search_vector": true,
"vector_candidate_count": 100,
"keyword_candidate_count": 100,
"merged_candidate_count": 200,
"included_count": 3,
"first_source": "vector"
}
```
排序原因:
```text
hybrid score 0.6326 = keyword 1.0000 * 0.55 + vector 0.1835 * 0.45; source=vector; matched_terms=押金
```
### vector:deposit refund
结果摘要:
```json
{
"retrieval_backend": "postgres-pgvector",
"vector_backend": "pgvector-hnsw",
"keyword_backend": "none",
"used_hnsw": true,
"used_search_vector": false,
"vector_candidate_count": 100,
"keyword_candidate_count": 0,
"merged_candidate_count": 100,
"included_count": 3
}
```
排序原因:
```text
vector score 0.2293; source=vector
```
### keyword:租赁
结果摘要:
```json
{
"retrieval_backend": "postgres-pgvector",
"vector_backend": "not_used",
"keyword_backend": "search_vector",
"used_hnsw": false,
"used_search_vector": true,
"vector_candidate_count": 0,
"keyword_candidate_count": 100,
"merged_candidate_count": 100,
"included_count": 3
}
```
排序原因:
```text
keyword score 1.0000; source=keyword; matched_terms=租赁
```
## 当前边界
- explain 现在能说明数据库检索路径和排序原因,但还没有记录每次 explain 的 SQL `EXPLAIN ANALYZE` 原文。
- 目前候选来源以 `vector`、`keyword`、`keyword+vector` 表达。对于同一 chunk 同时出现在两边的情况,可以进一步展示两边原始排名。
- explain 接口是管理员/调试用能力,正式法律问答仍通过 AI Trace 记录命中来源和质量标签。
## 下一步建议
下一步可以继续做:
1. 在 AI Trace 详情页展示 RAG explain 摘要,让每次法律问答能回看“为什么引用这些依据”。
2. 给 explain 增加向量原始排名、关键词原始排名、去重前后候选数。
3. 用真实法规库问题集跑“依据命中率 / 错误引用率”质量基线。