mirror of
https://github.com/Tencent/WeKnora.git
synced 2026-08-30 16:53:21 +08:00
feat(retriever): 接入 Apache Doris 4.1 作为向量数据库
为 RetrieveEngine 体系新增 Doris 后端,与现有 Qdrant/Milvus/Weaviate
等保持完整能力对齐:向量检索、关键词检索、健康检查、环境变量与多实例
DB 配置、前端类型注册、单元测试、Docker Compose 模板。
实现要点:
- 协议分工:主链路用 MySQL 协议(database/sql + go-sql-driver/mysql)
做 DDL / 查询 / 删除;批量更新走 Stream Load HTTP API,并启用
partial_update=true、merge_type=APPEND,自动按 1MiB 切分批次并处理
307 重定向。
- 表结构:UNIQUE KEY(id) + enable_unique_key_merge_on_write=true 以
支持 upsert/部分列更新;按维度分表(<base>_<dim>),每张表上建
HNSW ANN 索引(metric_type=cosine_distance)和 INVERTED 索引
(parser=chinese)。
- 分数语义:使用 cosine_distance_approximate,再以 1 - dist 转换为
"越大越相似",与现有 KVHybridRetrieveEngine 约定一致。
- 异步索引:ANN 索引为后台构建,ensureTable 通过轮询 SHOW INDEX 等
待索引就绪后再放行写入,避免首次检索召回为空。
- ARRAY<FLOAT> 序列化:go-sql-driver/mysql 不支持数组占位符,
embeddingLiteral 将 []float32 转成 SQL 字面量字符串再拼接。
新增文件:
- internal/application/repository/retriever/doris/{structs,schema,
query,repository,streamload,repository_test}.go
- scripts/e2e-doris.sh:E2E 验证清单
- docs/wiki/集成扩展/Doris改动与上游同步.md:fork-and-rebase 工作流
与改动清单
修改文件(接线 + 文档):
- internal/types/{retriever,tenant,vectorstore}.go:新增
DorisRetrieverEngineType、env 解析、表单 schema 与索引参数校验
- internal/container/{container,engine_factory}.go:环境变量驱动
与 VectorStore 配置驱动两条路径都支持 Doris
- internal/application/service/vectorstore{,_healthcheck}.go:连接
校验 + Ping/Version 健康检查
- docker-compose.yml:新增 doris-fe / doris-be 服务(profile=doris)
- .env.example:DORIS_* 环境变量与示例
- docs/{使用其他向量数据库,wiki/集成扩展/集成向量数据库}.md:
使用说明与索引/分数行为说明
依赖:go.mod/go.sum 新增 github.com/go-sql-driver/mysql(运行时)和
github.com/DATA-DOG/go-sqlmock(测试)。
测试:repository 层 SQL 形状、Stream Load HTTP 行为、whereBuilder
逻辑、embeddingLiteral 往返、健康检查错误路径均有单测覆盖。
This commit is contained in:
Executable
+73
@@ -0,0 +1,73 @@
|
||||
#!/usr/bin/env bash
|
||||
# Doris 4.1 端到端联调脚本
|
||||
#
|
||||
# 该脚本验证:
|
||||
# 1) 后端启动正常
|
||||
# 2) 通过 API 创建 Doris VectorStore
|
||||
# 3) 上传知识、写入索引
|
||||
# 4) 向量检索 + 关键词检索
|
||||
# 5) 关闭单个 chunk 后再检索(验证 BatchUpdateChunkEnabledStatus 走 Stream Load)
|
||||
#
|
||||
# 使用前置条件:
|
||||
# - docker compose --profile doris up -d 先把 Doris 起来
|
||||
# - 在 FE 上 CREATE DATABASE weknora;
|
||||
# - export RETRIEVE_DRIVER=doris && make run (或 docker compose up app)
|
||||
#
|
||||
# 这是"checklist-as-script",按需要手动逐段执行。
|
||||
set -euo pipefail
|
||||
|
||||
WEKNORA_API="${WEKNORA_API:-http://localhost:8080}"
|
||||
DORIS_FE_HOST="${DORIS_FE_HOST:-127.0.0.1}"
|
||||
DORIS_FE_HTTP_PORT="${DORIS_FE_HTTP_PORT:-8030}"
|
||||
DORIS_FE_MYSQL_PORT="${DORIS_FE_MYSQL_PORT:-9030}"
|
||||
|
||||
step() { printf '\n\033[1;36m==> %s\033[0m\n' "$*"; }
|
||||
|
||||
step "1. 检查 Doris FE 端口可达"
|
||||
nc -zv "$DORIS_FE_HOST" "$DORIS_FE_HTTP_PORT"
|
||||
nc -zv "$DORIS_FE_HOST" "$DORIS_FE_MYSQL_PORT"
|
||||
|
||||
step "2. 在 FE 上确认 weknora 库存在"
|
||||
docker exec WeKnora-doris-fe \
|
||||
mysql -h 127.0.0.1 -P 9030 -uroot \
|
||||
-e "CREATE DATABASE IF NOT EXISTS weknora; SHOW DATABASES;"
|
||||
|
||||
step "3. 通过 WeKnora API 创建 Doris VectorStore"
|
||||
curl -fsS -X POST "$WEKNORA_API/api/v1/vector-stores" \
|
||||
-H 'Content-Type: application/json' \
|
||||
-d '{
|
||||
"name": "doris-local",
|
||||
"engine_type": "doris",
|
||||
"connection_config": {
|
||||
"addr": "doris-fe:9030",
|
||||
"http_port": 8030,
|
||||
"database": "weknora",
|
||||
"username": "root",
|
||||
"password": ""
|
||||
},
|
||||
"index_config": {
|
||||
"collection_prefix": "weknora_embeddings",
|
||||
"buckets_num": 5,
|
||||
"replication_num": 1
|
||||
}
|
||||
}'
|
||||
|
||||
step "4. 上传一个简单知识库(这一步交给前端 UI 完成更省事)"
|
||||
echo "在前端 UI 切到刚才创建的 Doris VectorStore,新建知识库并上传一篇 PDF。"
|
||||
echo "或者用 curl + /api/v1/knowledges 调用 API。"
|
||||
|
||||
step "5. 在 FE 上验证表已建好"
|
||||
docker exec WeKnora-doris-fe \
|
||||
mysql -h 127.0.0.1 -P 9030 -uroot \
|
||||
-e "USE weknora; SHOW TABLES LIKE 'weknora_embeddings_%'; SHOW INDEX FROM weknora_embeddings_768;"
|
||||
|
||||
step "6. 检索验证"
|
||||
echo "在前端发起检索(向量 + 关键词),确认有命中。"
|
||||
echo "命中后到 FE 上查 SELECT COUNT(*) FROM weknora_embeddings_<dim>;"
|
||||
|
||||
step "7. 状态批改验证"
|
||||
echo "在前端把某个 chunk 关闭,再次发起检索,确认该 chunk 不再返回。"
|
||||
echo "FE 上确认 SELECT id, is_enabled FROM weknora_embeddings_<dim> WHERE chunk_id = '<id>';"
|
||||
|
||||
echo
|
||||
echo "全部步骤完成 → 联调通过"
|
||||
Reference in New Issue
Block a user