从 vector search 到强大的 REST APIs,Elasticsearch 为开发者提供了最全面的搜索工具包。您可以访问 Elasticsearch Labs repo 中的示例 Notebooks,尝试新功能。您也可以立即开始您的 免费试用,或在本地运行 Elasticsearch。
在 Elasticsearch 中查找与存储向量相似的文档,过去需要两次往返请求:首先使用 GET 获取向量,然后将其发送回 k-nearest neighbor (kNN) 查询中。Elasticsearch 9.4 通过 query_vector_builder.lookup 将这一流程合并为一次请求,简化了 API,并在双节点 Google Cloud Platform (GCP) 基准测试中,将延迟缩短了高达 3 倍。
以前,当您想查找与存储向量相似的文档时,需要执行以下步骤:
GET 从 Elasticsearch 中获取向量值。_search 调用中引用该向量值并发送回 Elasticsearch:这意味着您需要为两次请求支付序列化和网络成本:
在 Python 中,这种模式如下所示:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
from elasticsearch import Elasticsearch
es = Elasticsearch(HOST)
# 1) 从 Elasticsearch 获取种子向量
seed_doc = es.get(
index=source_index,
id=seed_id,
_source_includes=[vector_field],
)
query_vector = seed_doc["_source"][vector_field]
# 2) 在 kNN 查询中将其发回
resp = es.search(
index=target_index,
query={
"knn": {
"field": vector_field,
"k": 10,
"num_candidates": 100,
"query_vector": query_vector,
}
},
)
尽管这两个调用看起来成本不高,但产生的开销是不必要的。让我们来改进它。
query_vector_builder.lookup 在 Elasticsearch 9.4 中的工作原理在 Elasticsearch 9.4 中,我们添加了 lookup 功能,以简化 API 并消除不必要的成本:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
from elasticsearch import Elasticsearch
es = Elasticsearch(HOST)
resp = es.search(
index="products",
query={
"knn": {
"field": "product-vector",
"k": 10,
"num_candidates": 100,
"query_vector_builder": {
"lookup": {
"index": "seed-products",
"id": "product-123",
"path": "product-vector"
}
},
}
},
)
现在,这个请求会从 seed-products 索引中 ID 为 product-123 的文档的 product-vector 字段中获取 dense_vector 值。这个示例是一个“更多类似”的搜索,用于查找与 ID 为 product-123 的向量最近的向量。您可以引用任何索引,从而有效地将 lookup 用作查询向量存储。
lookup 向量搜索能减少多少延迟我们的目标是简化用户体验并提高速度。性能提升不仅仅来自于消除客户端的往返请求。许多 Elasticsearch 实例涉及多个节点,节点间的流量会产生自身的序列化和网络成本。Elasticsearch 会主动将执行偏向本地节点,这也在服务器端减少了网络序列化成本。
为了说明潜在的性能改进,这里是我们进行的一项基准测试。我们使用了修改版的 so_vector 工具,其中一条路径采用 GET 后接 _search 模式,另一条路径则使用 lookup。在 GCP 同一区域的两个节点上运行,结果非常出色。延迟始终提高了近 3 倍。即使节点位于同一数据中心和同一可用区内,网络和序列化成本仍可能产生实际影响。
百分位数 | get-then-knn (毫秒) | lookup-knn (毫秒) | 减少百分比 | 速度提升倍数 |
|---|---|---|---|---|
p50 | 10.3796 | 3.14093 | 69.74% | 3.30x |
p90 | 25.4429 | 5.89807 | 76.82% | 4.31x |
p99 | 27.7167 | 8.07109 | 70.88% | 3.43x |
max (p100) | 28.522 | 12.6497 | 55.65% | 2.25x |
此基准测试在 200 万个文档上运行,延迟的改善将取决于您的整体搜索成本。即使速度提升较小,lookup 仍然消除了额外的客户端请求。代码更少,往返次数更少。
有时候,微小的改变也能产生巨大的影响。虽然这是一个简单的功能,但我希望它能消除您在使用 Elasticsearch 时一些不必要的摩擦,并使我们更受喜爱。
📡 更多 Elastic & AI 可观测性干货