马赛克 AI 矢量搜索是为快速、可缩放的检索而构建的。 矢量搜索性能取决于许多因素,包括 SKU 选择、索引大小、查询类型、矢量维度、身份验证方法,以及应用程序处理流量高峰的方式。 大多数工作负荷都开箱即用,但对于需要缩放或优化延迟的情况,本指南提供了实用提示和常见模式,可帮助你配置系统以实现最佳矢量搜索性能。
影响性能的因素
性能不是一个数字 , 它是一个范围,具体取决于工作负荷特征、配置选项和客户端实现。 本指南旨在帮助你构建一个明确的心理模型,说明性能的工作原理,以便你最有效地使用马赛克 AI 矢量搜索。
以下是影响系统行为方式的关键因素:
- SKU 选项:标准型或存储优化型。
- 索引大小:存储的矢量数。
- 嵌入大小:通常为 384–1536。
- 查询类型:近似最近邻(ANN)或混合。
- 请求的结果数:较高的值会增加检索时间。
- 嵌入类型:托管或自管理。
- 查询负载:流量随时间推移达到终结点的次数。
- 身份验证方法:应用如何连接到 Databricks。
本文的其余部分提供了用于优化每个变量的实用提示,并说明了它们如何影响实际部署中的搜索延迟和查询吞吐量。
选择正确的 SKU
马赛克 AI 矢量搜索提供两个 SKU,每个 SKU 旨在根据工作负荷平衡延迟、可伸缩性和成本效益。 为应用程序选择正确的 SKU 是优化性能的第一个杠杆。
一般而言:
- 当延迟至关重要且索引低于 320M 矢量时,请选择标准终结点。
- 在处理超过 1000 万个矢量时,如果可以接受一定的额外延迟,并且需要获得更好的每个向量的成本效益(最多可节省 7 倍),请选择存储优化端点。
下表显示了一些预期的性能准则。
| SKU | 延迟 | QPS | 索引容量 | 矢量搜索单元 (VSU) 大小 |
|---|---|---|---|---|
| 标准 | 20–50 毫秒 | 30–200+ | 320百万矢量 | 2M 向量 |
| 存储优化 | 300–500 毫秒 | 30–50 | 1B 向量 | 64M 向量 |
了解索引大小
当索引适合单个矢量搜索单元时,性能最高,具有额外的空间来处理其他查询负载。 随着工作负荷扩展到单个矢量搜索单元(即标准配置为 200 万+ 矢量,或存储优化为 6400 万+ 矢量),延迟增加,QPS 减少。 最终,QPS 约为 30 QPS (ANN),达到上限。
性能取决于每个工作负荷特有的许多因素,例如查询模式、筛选器、矢量维度和并发。 以下数字是参考点。
| SKU | 向量 | 尺寸 | 延迟 | QPS | 每月查询 |
|---|---|---|---|---|---|
| 标准 | 10K | 768 | 20 毫秒 | 200+ | 500M+ |
| 10M | 768 | 40ms | 30 | 78M | |
| 100兆字节 | 768 | 50 毫秒 | 30 | 78M | |
| 存储优化 | 10M | 768 | 300 毫秒 | 50 | 130M |
| 100兆字节 | 768 | 400ms | 40 | 100兆字节 | |
| 1B | 768 | 500 毫秒 | 30 | 78M |
最小化嵌入大小
矢量维度是指每个向量中的特征数。 典型值为 384、768、1024 或 1536。 更高的维度提供更具表现力的表示形式,可以提高质量,但需要计算成本。 在检索期间,低维向量需要更少的计算,这转化为更快的查询时间和更高的 QPS。 相反,高维向量会增加计算负载并减少吞吐量。
作为一般规则,请选择为用例保留检索质量的最小维度。
例如,将维数减少为 2(例如,从 768 到 384)通常将 QPS 提高约 1.5 倍,并根据索引大小和查询模式将延迟减少约 20%。 这些增益在极低维度情况下进一步累积。 例如,与表中所示的 768 维度基准相比,使用 64 维向量可提供显著提高的 QPS 和显著较低的延迟。 这使得 384 个维度和更低维度对高吞吐量、延迟敏感的用例特别有吸引力,只要检索质量仍可接受。
使用人工神经网络提高效率,并在必要时使用混合方法。
尽可能使用 ANN 查询。 它们是最高效的计算,支持最高的 QPS。
必要时使用混合搜索。 混合搜索提高了某些应用程序的召回能力,尤其是在特定领域关键字重要的情况下。 混合搜索通常使用比 ANN 多一倍的资源,并且可以显著减少处理能力。
使用 10–100 个结果
每个查询都包含一个 num_results 参数,该参数是要返回的搜索结果数。 此值直接影响性能。 检索更多结果需要对索引进行更深入的扫描,从而增加延迟并减少 QPS。 随着值的增高,效果变得更加显著。 例如,增加 num_results 10 倍可能会增加查询延迟,并根据索引大小和配置将 QPS 容量减少 3 倍。
最佳做法是,除非应用程序特别需要更多,否则请保持在 num_results 10-100 的范围内。 使用实际查询尝试不同的 num_results 值,以了解对工作负荷的影响。
避免生产规模到零
矢量搜索支持具有不同性能权衡的两种类型的嵌入。
托管嵌入是最方便的。 借助托管嵌入,Databricks 会自动为行和查询生成嵌入内容。 在查询时,查询文本将传递给提供终结点的模型,以生成嵌入,从而增加了延迟。 如果嵌入模型是外部的,则它还会产生额外的网络开销。
通过自管理嵌入,可以提前计算嵌入内容,并在查询时直接传递向量。 这可以避免运行时生成并启用最快的检索。 本文中包含的所有性能数字都基于自管理嵌入。
对于实时生产用例,请避免缩放到零的模型终结点。 如果终结点在查询到达时处于非活动状态,冷启动可能会延迟几分钟的响应,甚至会导致失败。
规划查询高峰
本部分介绍流量增加时可能会发生的情况,以及如何在触发延迟峰值或 429 错误(请求数量过多)的关键限制之下保持。
当负载适中时,延迟会保持较低,在接近最大 QPS 容量时逐渐增加。 当系统达到 100% QPS 容量时,它将开始返回 429 错误。 如果尚未设置适当的退避,应用可能会无响应。
429 个错误充当保护系统的安全机制。 它们指示客户端稍后返回并重试,以便终结点保持正常运行和响应能力,即使在突然的流量高峰下也是如此。
最佳做法是使用 矢量搜索 Python SDK,其中包括内置的退避和重试处理。
如果使用 REST API,请实现带有抖动的指数退避算法。 请参阅 Azure 反模式。
将服务主体与 OAuth 令牌配合使用
使用高效的身份验证方法获得最佳性能。 Databricks 建议在所有生产环境中 将服务主体与 OAuth 令牌 配合使用。 OAuth 访问令牌提供更高的安全性,还利用网络优化基础结构,使系统能够以全容量运行。
避免使用个人访问令牌(PAT),因为它们会引入网络开销,增加数百毫秒的延迟,并显著降低终结点可承载的 QPS。
使用 Python SDK
使用最新版本的 Python SDK 受益于内置性能和可靠性优化。
在查询中重复使用索引对象。 避免在每个请求中调用 client.get_index(...).similarity_search(...) ,因为此模式会增加不必要的延迟。
而是初始化索引一次,并重复使用它:
# Initialize once
index = client.get_index(...)
# Then use it for every query
index.similarity_search(...)
在 MLFlow 环境中使用矢量搜索索引时,这一点很重要,可以在终结点初始化时创建索引对象,然后为每个查询重复使用该索引对象。
本指南在实时、延迟敏感的应用程序中特别有用。 在具有多个索引或 代表用户授权 流的 RAG 设置中,索引选择或凭据仅在查询时可用,初始化索引对象一次可能不可行。 这些情况下不需要此优化。
跨终结点并行化
Databricks 建议探索以下策略以增加系统中的总 QPS:
- 在不同端点之间拆分索引。 如果有多个索引,每个索引都接收大量流量,请在单独的终结点上托管这些索引,以达到更高的总带宽。
- 将索引复制到多个终结点。 如果大多数流量集中在单个索引上,请跨多个终结点复制该索引。 在客户端级别均匀拆分流量,以获取线性 QPS 增益。