本系列以 Milvus 2.6.x 钉住专用向量引擎内核(01–14),用 Qdrant 与 Lance 做对照(15–16),并用症状到机制的决策树把排障接到症状(17)。本文给出 扩展后的选型决策树、扩展后的站内阅读地图 与 仍开放的问题——不代替官方容量规划,不排名「谁全局最快」。
本文是「向量检索引擎」系列第 18 篇(共 19 篇)。→ 系列目录
同进程 SQL 扩展的页模型与 Index AM 钉点见续篇 19 pgvector 内核对照。
一、决策树(扩展版)
相对第 15–17 篇给出的对照坐标,选型时通常还要多问几个问题:数据是否已经在湖上、是否必须留在 SQL 同一进程、团队能否运维存算分离、规模是否到十亿级、是否需要强多租户隔离。把这些判断串成一条决策链:
flowchart TD
start["Need approximate nearest neighbor?"]
start -->|"no"| stop["Skip vector stack"]
start -->|"yes"| online["Online low-latency + continuous write?"]
online -->|"no"| lakeGate["Data already in lake + need snapshot/random take?"]
lakeGate -->|"yes"| lance["Lance ± LanceDB<br/>见第 16 篇, lakehouse/21"]
lakeGate -->|"no"| batchGate["Batch / low QPS prototype?"]
batchGate --> embeddedQdrant["Single-node Qdrant or embedded lib<br/>见第 15 篇"]
online -->|"yes"| sqlGate["Must stay in same process as SQL/OLTP transactions?"]
sqlGate -->|"yes"| pg["pgvector to start<br/>见第 19 篇内核;规模上来再迁出"]
sqlGate -->|"no"| opsGate["Team can operate multi-component disaggregation?"]
opsGate -->|"no"| qdrantCluster["Qdrant single node or shard+replica cluster<br/>见第 15 篇"]
opsGate -->|"yes"| scaleGate["Billion-scale or need independent index-build pool?"]
scaleGate -->|"no"| milvusSmall["Milvus small cluster<br/>本系列 01-14"]
scaleGate -->|"yes"| tenantGate["Strong multi-tenant isolation + multiple consistency levels required?"]
tenantGate -->|"yes"| milvusFull["Milvus full cluster, dedicated Data Node pool<br/>见第 10、12、14 篇"]
tenantGate -->|"no"| qdrantShard["Qdrant shard+replica cluster<br/>注意 Raft 3 节点门槛,见第 15 篇第五节"]
相比第 15–16 篇分别给出的双边对照,这张图把「湖 vs 在线」「同进程 SQL vs 独立引擎」「能否运维存算分离」「规模」「多租户隔离」五个判断轴串成一条路径——任何一个判断轴给出的答案都可能推翻上一轮的直觉结论,这正是选型不能只看一张对比表的原因。
1.1 边界说明
| 选项 | 选它时你在买什么 | 主要代价 |
|---|---|---|
| Milvus | Growing/Sealed、一致性级别、离线建索隔离、对象存储弹性 | 组件多;对象 API 与协调者运维 |
| Qdrant | 少组件、payload 过滤、分片副本对称集群、Raft 管拓扑 | 超大规模时垂直/分片运维模型不同;高可用要求 ≥3 节点(第 15 篇第五节) |
| Lance | 湖侧随机访问与版本化向量子集 | 不是完整在线多租户引擎;索引批量重建节奏(第 16 篇第四节) |
| pgvector | 与 PostgreSQL 事务/SQL 同进程 | 与 OLTP 争资源;大规模常需迁出;页模型见 第 19 篇 |
这张表刻意不填具体的成本数字(如”每月多少运维人力”),因为这类数字强依赖团队规模、云厂商定价与已有基础设施,本系列没有可引用的通用数据。但表格本身已经指向一个可操作的思路:把”主要代价”这一列翻译成你团队现有的能力清单——如果团队里没有人熟悉 etcd/对象存储运维,Milvus 那一行的代价会被放大;如果团队已经有成熟的 Kubernetes 平台在跑其它分布式系统,这部分代价可能已经被摊薄。选型对照表给出的是”代价的类型”,不是”代价的绝对值”,绝对值永远要代入自己团队的现状。
二、最小故事:一个团队从原型到十亿级的选型迁移
设想一个做企业知识库 RAG 的团队,选型经历了三个阶段,每次迁移都对应决策树上一个具体的判断轴翻转:
阶段一(原型,几万条文档):团队最初把向量列直接加进已有的
PostgreSQL 库,用 pgvector 做检索——决策树上
sqlGate
走「是」这条分支:产品还在验证阶段,团队不想为向量检索单独运维一套系统,SQL
事务与检索共用同一个连接池简化了应用层代码。
阶段二(增长,几百万条文档,QPS
上升):随着检索并发上升,pgvector 与 OLTP
查询开始争抢同一个数据库实例的内存和
CPU(sqlGate
分支已写明的代价),团队把向量检索拆成独立服务。这时候团队规模还小,不想维护
etcd/对象存储/多 Worker,选择单节点 Qdrant——决策树上
opsGate 走「否」:不是 Qdrant
能力不够,而是团队当前不需要存算分离换来的弹性,少组件带来的运维简单更值钱。
阶段三(十亿级,多租户):产品做成多租户
SaaS,每个客户的知识库要严格隔离,且不同客户对「新文档写入后多久能被搜到」的要求不同(有的客户能接受秒级陈旧,有的要求写完立刻可见)——这直接对应
tenantGate
里的「多一致性级别」需求。同时数据量涨到十亿级,建索引的计算需求开始和在线查询争抢资源。团队这时候迁到
Milvus 集群,把 Data Node 单独拆成资源池(第 10
篇),并按客户使用不同的一致性级别(第 12 篇)。
这个故事要传达的核心结论是:选型不是一次性决策,而是随着规模和团队能力变化、沿着决策树重新走一遍的过程;三个阶段没有一个是「错误的选择」,每个选择在当时的判断轴取值下都是合理的。真正的风险是在阶段一就为阶段三的规模过度设计(提前上 Milvus 集群),或者在阶段三还留着阶段一的架构(多租户压力下仍用同进程 pgvector)。
三、回到五个关键问题
| 问题 | 本系列落点 |
|---|---|
| 向量库 vs 带向量列的库差在哪层? | 01、02、18 |
| insert → Growing → Sealed + Index? | 03–06、10 |
| search 如何拼 Growing/Sealed 并归并?Knowhere 在哪? | 07–09 |
| 过滤为何毁掉召回/延迟? | 11(+ frontier/09) |
| 十亿级选谁? | 15–18 |
四、站内阅读地图(扩展版)
在第一版按「目标读者」给路径的基础上,补一张按 系列内部分工 组织的地图,说明本系列各部分如何依次承接相邻系列,再把结论交给 RAG 应用层:
flowchart LR
frontier["db-frontier 08/09<br/>ANN & hybrid filter algorithms"]
lake["lakehouse/21<br/>Lance lake side"]
subgraph engine ["This series: engine internals"]
direction TB
model["01-03<br/>model & state machine"]
write["04-06<br/>write path & WAL"]
read["07-10<br/>read path & index"]
fc["11-14<br/>filter / consistency / replica"]
compare["15-18<br/>compare & selection"]
model --> write --> read --> fc --> compare
end
rag["llm-infra 17/18<br/>RAG application"]
frontier --> model
lake --> compare
compare --> rag
| 目标 | 路径 |
|---|---|
| 只搞懂算法 | frontier/08 → 本系列 02、08 |
| 从 RAG 下沉 | llm-infra/17–18 → 01 → 03 → 07 → 11 → 12 → 18 |
| 湖上向量 | lakehouse/21 → 16 →(若要在线)15 或 Milvus 01 |
| 排障 | 17 → 按第 17 篇决策树回链各篇 |
| 写路径深挖 | 03 → 05 → 06 → 10 → 13 |
| 读路径深挖 | 07 → 08 → 09 → 11 → 12 → 14 |
| 只看选型不看内核 | 15 → 16 → 17(对照与排障) → 本篇 |
五、与 llm-infra RAG 的接线
llm-infra/17 管 chunking、召回、rerank;18 管产品选型直觉。本系列补上:
- 入库后 多久、在何种一致性下 可搜(12);
- 权限/属性过滤如何进引擎(11);
- 撤回文档如何 delete 并回收(13);
- 延迟尖刺看水位还是看建索(17)。
RAG 效果差时,先分清是 检索工程 还是 生成/Prompt——向量引擎只对前者负责。
六、决策树之外:如何用自己的数据做一次验证
第一节的决策树能帮你缩小候选范围,但真正下决定前,值得用自己的数据跑一次小规模验证,而不是只凭架构对照表拍板。一个可复现的验证流程,覆盖本系列反复强调的几个容易被对比表忽略的维度:
- 用真实查询分布,不是均匀随机向量:第 11 篇已经说明选择度和向量语义的相关性会显著影响过滤路径的实际代价;如果业务查询天然带过滤条件,验证时必须带上真实的过滤字段分布,均匀随机数据测出的延迟数字对生产没有预测力。
- 测到 P99,不要只看均值:第 12 篇的一致性等待、第 14 篇的冷段加载都是尾部现象,均值很可能完全掩盖这些机制引入的偶发延迟——候选系统之间的差异往往先在 P99 显现,再影响均值。
- 模拟真实的写入节奏,不只是静态数据集打分:第 13 篇的软删/compaction、第 10 篇的建索队列都是”持续写入”场景下才会暴露的行为;只用一次性灌入的静态数据集做 benchmark,测不出这类系统在生产写入压力下的表现。
- 记录运维动作发生时的行为,不只是稳态数字:第 14 篇的滚动升级、第 15 篇的 Raft 节点增减,都会在变更窗口内产生短暂的行为变化(等待、重路由);如果验证时从不触发这类运维动作,会错过候选系统在这些时刻的真实表现,等到生产环境第一次做运维操作时才发现问题。
- 按第一节的判断轴打分,不是按单一指标排名:验证结束后,把结果代入决策树的具体判断轴(在线性、SQL 同进程需求、运维能力、规模、多租户),而不是简单地说”系统 A 延迟更低所以选 A”——延迟只是其中一个维度,运维复杂度和团队能力同样是决策变量。
这五步的共同原则是让验证环境尽量还原生产会遇到的条件(过滤、持续写入、运维动作),而不是只在理想稳态下测一个数字——本系列多次强调”同一套参数在测试环境快、生产环境慢”(第 11 篇开篇故事就是一例),选型验证阶段犯同样的错误,代价是把问题带到生产才发现。
七、常见误解
误解一:选型就是找一份对比表,挑分数最高的那个。 第一节的决策树刻意不给「综合评分」,因为不同判断轴的权重因团队而异——一个能承受存算分离运维成本的团队和一个不能的团队,即使数据规模相同,合理选择也不同。对比表能列功能差异,但「哪个更重要」永远是你自己的约束条件决定的,不是表格本身。
误解二:开源 = 零运维成本,随便选一个自建就行。 第 15 篇已指出 Qdrant 高可用要求至少三个 Raft 投票节点;本系列 01–14 已反复说明 Milvus 存算分离需要 etcd、对象存储、多类 Worker 协同运维。开源意味着不用付license费,不意味着运维投入为零——第二节故事里团队在阶段二选单节点 Qdrant,本质就是在承认「现在没有能力运维分布式高可用集群」。
误解三:一旦选定 Milvus 或 Qdrant,架构就锁定了,后续想换代价极高。 第二节的故事展示了一条从 pgvector 到单节点 Qdrant 再到 Milvus 集群的真实迁移路径。只要保留「向量与其业务 id、来源可回溯」这个基本约束(不依赖某个引擎的内部 id),迁移的主要成本是重新写入与索引重建,不是不可逆的架构债务。真正昂贵的是在数据规模远超需求前就过度设计。
误解四:pgvector
只适合玩具项目,正式生产必须换专用引擎。
边界说明表已列出 pgvector 的定位:「与 PostgreSQL 事务/SQL
同进程」是一个真实的产品诉求,不是能力不足的妥协。只要规模与并发没有触发第一节
sqlGate
之后的资源争抢问题,同进程方案完全可以是生产选择,「必须换」是没有对照约束条件的空话。
误解五:选型验证只要跑一次 benchmark 拿到延迟和召回数字,就能确定生产表现。 第六节已经列出验证时容易被忽略的维度:真实过滤分布、P99 尾延迟、持续写入压力、运维动作窗口。只测均值延迟和静态数据集召回,测不出第 12、13、14 篇反复强调的那些”稳态之外”的行为——延迟数字好看不代表生产不会踩坑,验证的覆盖面比单次数字的精度更重要。
八、学术谱系与开放问题(系列收束)
8.1 谱系:本系列钉过的核心论文一览
把 01–17 篇引用过的核心论文按主题收束一次,帮助读者判断「哪些结论有一手学术依据、哪些是工程规范」:
| 主题 | 核心文献 | 系列落点 |
|---|---|---|
| 向量数据管理系统 | Wang et al., Milvus, SIGMOD 2021 | 第 1、8、9、10 篇:系统论文与 2.6.x 实现的谱系差 |
| ANN 图索引 | Malkov & Yashunin, HNSW, TPAMI 2020 | 第 1、8 篇:算法假设外链 frontier/08 |
| 磁盘驻留 ANN | Subramanya et al., DiskANN, NeurIPS 2019 | 第 1、8 篇:与 Knowhere 默认内存假设对照 |
| 混合过滤 | Patel et al., ACORN, SIGMOD 2024 | 第 11 篇:选择度与图感知检索 |
| MPP 归并 | Graefe, Exchange 算子, SIGMOD 1990 | 第 9 篇:三级 reduce 树的经典源头 |
| 有界陈旧 | Bailis et al., PBS, VLDB 2012 | 第 9、12 篇:与 Bounded 一致性的概率化对照 |
| 会话一致性 | Terry et al., Session Guarantees, PDIS 1994 | 第 9、12 篇:与 Session 级别命名对照 |
| LSM 不可变文件整理 | O’Neil et al., LSM-Tree, Acta Informatica 1996 | 第 3、10、13、16 篇:Growing/Sealed、compaction、Lance 删除文件同构 |
| leveled/tiered 权衡 | Dayan & Idreos, Dostoevsky, SIGMOD 2017 | 第 10 篇:姊妹领域对照,未代入 Milvus 具体实现 |
| 共识协议 | Ongaro & Ousterhout, Raft, USENIX ATC 2014 | 第 15 篇:Qdrant 拓扑管理的直接来源 |
| 分布式追踪 | Sigelman et al., Dapper, 2010 | 第 17 篇:排障方法论对照 |
这张表本身回答了一个容易被忽视的问题:「向量数据库」不是一个孤立的新领域,它的关键设计决策(后台整理、归并树、一致性折中、共识协议)分别落在数据库与分布式系统几十年的既有谱系里,只是叠加了「高维近似检索」这一个新维度。
8.2 开放问题(系列收束)
- GPU 索引工业化:Knowhere 支持 GPU 路径(第 8 篇),多租户下设备内存碎片与抢占仍缺标准答案。
- 多向量 / 多模态字段:单实体多 embedding 时的索引生命周期与混合评分(第 3、8、10 篇都留了对应的开放问题分支)。
- 稀疏 + 稠密融合:学习稀疏与稠密 ANN 的统一执行与过滤(与 ColBERT 等应用层分工)。
- 湖表与在线引擎的版本原子性:Iceberg snapshot ↔︎ Lance manifest version ↔︎ Milvus 可见集三边没有统一协议对齐(第 16 篇第六节已展开三边对齐的应用层做法)。
- 过滤自适应:按选择度自动切换 pre/post/in-filter 与候选倍数(11、frontier/09)。
- 统一可观测性:第 17 篇已指出「召回/延迟/队列深度」缺一个跨组件的红黄绿看板模板,这是本系列反复触及但未解决的运维缺口。
- 标准化的向量引擎选型验证套件:第六节给出的五步验证方法目前只是本系列总结的方法论,业内没有一套类似 TPC-H/YCSB 那样覆盖”过滤 + 持续写入 + 运维动作”三个维度的公开标准 benchmark,各团队各自造轮子,结果互相不可比。
九、系列完成状态
| 部分 | 篇目 | 状态 |
|---|---|---|
| 生态与模型 | 01–03 | 已发布 |
| 写路径 | 04–06 | 已发布 |
| 读路径与索引 | 07–10 | 已发布 |
| 过滤/一致性/变更 | 11–14 | 已发布 |
| 对照与收束 | 15–18 | 已发布 |
实验台账中的 Docker 小规模实测仍可按 PLAN.md 后续补强;正文机制不依赖未跑数字。
十、小结
三句话小结:专用向量引擎解决的是 持续写入、近似检索、过滤、分布式生命周期,湖格式解决 版本与随机访问,pgvector 解决 同进程 SQL——选型是按负载在这三层之间选位置,不是按热词选库;决策树上的每一个判断轴(在线性、SQL 同进程、运维能力、规模、多租户)都可能推翻上一轮结论,选型因此是一个随规模演进重新走一遍的过程,不是一次性赌注;本系列涉及的关键机制大多能追到数据库与分布式系统的既有学术谱系(LSM、MPP 归并、共识协议、有界陈旧),向量检索是叠加了高维近似这一新维度,不是凭空出现的新领域。
感谢读完 18 篇——从 系列目录 可按角色路径回看。
参考资料
- 本系列 index 与第 1–17 篇(核心论文清单见第 8.1 节)。
- db-frontier/08–09、llm-infra/17–18、lakehouse/21。
- Milvus / Qdrant / Lance 官方文档(各篇已列)。
同主题继续阅读
把当前热点继续串成多页阅读,而不是停在单篇消费。
【向量检索引擎】Milvus · Segcore · Knowhere · Qdrant · Lance · pgvector
补齐 ANN 算法与 RAG 应用之间的生产级向量引擎层:以 Milvus 2.6.x 为主线拆解 Segment、WAL、Segcore、Knowhere、混合过滤与一致性,并用 Qdrant、LanceDB、pgvector 对照选型。
【向量检索引擎】向量引擎全景:算法、RAG 与专用引擎之间的一层
定位专用向量检索引擎相对 ANN 算法、RAG 应用与湖仓格式的分工;以 Milvus 2.6.x 四层架构与 insert/search 最小故事建立坐标系,并交代从 SIGMOD 2021 到 Streaming 演进的谱系与常见误解。
【向量检索引擎】Qdrant 对照:单库路径、payload 过滤与分片副本
对照 Qdrant 与本系列 Milvus 主线:Segment 内的向量/payload/id mapper 三件套、WAL+序号版本化、后台 optimizer 四类任务,以及 Raft 只管拓扑不管点操作的分布式模型;说明何时单进程/小集群更合适。
【向量检索引擎】Lance / LanceDB 对照:格式还是服务
承接 lakehouse/21 的 Lance vs Parquet 实测口径,用官方 Table Format 规范拆开 fragment/manifest/version 与 Milvus Segment/WAL 的边界;对照两边索引异步构建的共性,并给出湖侧 snapshot 与在线引擎可见性水位的对齐方式。