作者:来自 Elastic Matthew Adams

如何为你的搜索应用程序添加监测,以使用现代的 Open Telemetry 标准,为你的搜索和用户提供洞察。
Elasticsearch 包含丰富的新功能,帮助你针对你的使用场景构建最佳搜索解决方案。在我们的现代 Search AI 体验构建实践网络研讨会中,了解如何将它们付诸实践。你还可以立即开始免费的云试用,或者立即在你的本地机器上试用 Elastic 。
了解哪些搜索能够带来收入,哪些搜索会流失客户,无需单独的分析管道。使用 OpenTelemetry (OTel) 将搜索行为作为属性添加到你现有的应用程序请求中,并在 Elastic 中查询点击率、零结果查询和转化漏斗,同时解锁现代应用性能监测。如果你已经在运行 Elastic ,那么你已经拥有所需的一切。本文将向你展示如何实现。
你将了解的内容
在本文中,你将了解:
- 全面搜索分析技术栈的价值。
- 在搜索分析中使用现代可观测性标准的理由。
- 将搜索分析与可观测性相结合的优势。
- 开始实践的第一步。
搜索分析挑战
你的产品经理想知道哪些搜索正在推动购买,哪些搜索正在流失客户。为了回答这个问题,你必须 grep 5GB 的 Nginx 日志,将它与购买数据的 CSV 文件连接起来,并祈祷时间戳能够对齐。一定有更好的方式。
这些问题看起来很简单:
-
哪些搜索会带来收入,哪些搜索会流失客户?
-
用户是否找到了他们正在寻找的内容?
-
哪些查询失败了?
-
如何将搜索行为与业务结果连接起来?
获取答案更加困难。传统方法涉及拼接自定义事件管道、第三方分析工具和手工制作的仪表板。最终你会得到数据孤岛:这里是搜索日志,那里是点击事件,而业务指标则完全在其他地方。
如果有一种更简单的方法呢?
引入 OpenTelemetry(以及为什么它适合搜索)
如果你来自搜索工程背景,你可能没有接触过 应用程序性能监测(APM) ,它是一种通过为代码添加监测来了解代码在生产环境中如何运行的实践。现代 APM 背后的核心理念是 追踪(trace),它是一种结构化记录,用于跟踪单个请求如何流经你的系统,从最初的 API 调用到每一次数据库查询和服务跳转。与日志不同,日志是孤立的文本行,而追踪可以连接整个技术栈中的各个环节。
OpenTelemetry(OTel)已经成为生成这些追踪的行业标准。它由 OpenTracing 和 OpenCensus 合并而来,提供了一种与供应商无关的方式来收集追踪、指标和日志。核心理念很简单:只需对代码添加一次监测,然后将数据发送到任何地方。
Elastic 作为贡献者,已经在这个标准上投入了大量资源。Elastic 积极让其 Elastic Common Schema (ECS) 与 OTel Semantic Conventions 保持一致,使字段名称在两者之间保持一致,并且它将 Universal Profiling Agent 捐赠给 OTel 项目,使分析成为核心 OTel 信号。
由于这种一致性,Elastic 原生理解 OTel 数据。OTel 使用 OpenTelemetry Protocol(OTLP)传输数据。在 Elastic Cloud 上,托管的 OTLP 端点 (mOTLP)可以直接从你的 SDK 接收 OTLP spans,而无需中间收集器。对于自管理部署,Elastic Distribution of OpenTelemetry (EDOT) Collector 提供相同的路径。这使你可以使用标准 OTel 追踪进行搜索分析,而无需任何额外基础设施。
追踪如何变成分析
一个 trace 是一组 spans,其中每个 span 代表一个操作(一次 API 调用、一次数据库查询或一次搜索请求)。每个 span 都可以携带任意 attributes(描述发生了什么的键值对)。
这就是搜索变得有趣的地方。搜索行为可以依托 OTel 已经为 APM 生成的相同 spans,无需添加新的 attributes,只需扩展现有调用即可。
-
search.query:用户搜索的内容。 -
search.result_count:返回了多少结果。 -
search.result_click_position:用户点击了哪个结果。
通过使用这些 attributes 扩展 OTel,我们可以使用支持应用程序监测的相同基础设施捕获丰富的行为数据。你不需要新的管道或新的供应商;你只是在现有 spans 中添加新的 attributes。
统一方案:OTel + Elastic + ES|QL
如果你正在构建搜索,那么你很可能已经在运行 Elasticsearch。它为数千个 电子商务 网站、内容平台和企业应用程序提供搜索能力。它通常因其速度、灵活性以及 向量搜索、学习排序(LTR)和查询规则等功能而被选择。搜索社区中较少为人知的是,Elastic 也在可观测性领域进行了超过十年的投入。Elastic APM、日志记录和基础设施监测已经在各个行业大规模使用。
在同一个平台上运行搜索和可观测性,正是这种方法有效的原因。运行你的搜索引擎的同一个平台,也可以分析人们如何使用它。Elastic 通过其托管 OTLP 端点原生摄取 OTel 数据,而 Elasticsearch 查询语言(ES|QL),即 Elasticsearch 的管道式查询语言,可以轻松地在 Kibana 中探索和聚合这些数据。
结合起来,它们为搜索分析提供了一种很有吸引力的方法:
-
一次监测:将 OTel attributes 添加到你的搜索请求和用户交互中。
-
集中存储:追踪通过 mOTLP 流向 Elastic,与其他应用程序遥测数据一起存储。
-
灵活查询:在 Kibana 中使用 ES|QL 计算指标,按任意 维度 切分数据,并探索模式。
你不需要单独的分析管道或专用的点击追踪服务。你只需要对你的搜索应用程序进行适当的监测。
你可以测量的内容
通过正确的监测,你可以回答重要的问题:
搜索质量指标
-
CTR:多少比例的搜索会产生点击?低 CTR 可能表示相关性较差或结果展示不够吸引人。
-
平均倒数排名(MRR):当用户点击时,他们会在结果列表中向下找到多远?MRR 为 1.0 表示每次点击都位于第 1 位。如果每个人都点击第 2 位的结果,你的 MMR 将会是 0.5。越高越好。
-
零结果率:多少比例的搜索没有返回任何内容?这些是你的内容缺口或查询解析失败。每一次零结果搜索都是一次错失的机会。
查询级别分析
除了聚合指标,你还可以深入分析具体查询:
-
按数量排名靠前的查询:用户实际搜索了什么?
-
低 CTR 查询:相关性在哪里失败?
-
零结果查询:你的索引中缺少哪些内容?
-
点击位置分布:点击是否集中在顶部,还是分散在不同位置?
业务影响
搜索并不是孤立存在的。通过跟踪从搜索到转化的过程,你可以将相关性与收入连接起来:
-
哪些搜索会产生加入购物车事件?
-
搜索与浏览相比,转化率是多少?
-
哪些查询带来了最多收入?
用于机器学习的训练数据
用于衡量搜索质量的相同点击数据,也可以用于训练模型以改进搜索质量。点击位置和频率可以转换为 LTR 模型的判断列表,将用户行为转化为相关性信号。
Kibana 中的搜索分析仪表板示例
下面是在实践中的样子。这个 Kibana 仪表板完全由 OTel 追踪和 ES|QL 驱动,没有自定义管道或单独的分析服务:

这个仪表板上的每个面板都来自同一个索引。核心指标使用基于数值的着色来一目了然地显示健康状态:CTR 和 MRR 为绿色(健康 ),而零结果率为红色(需要关注)。下面,你可以看到哪些查询带来了最多点击,哪些查询没有返回任何内容,以及搜索如何通过漏斗转化为收入。
注意底部的 SLO 卡片,其中包含类似"99% 的搜索低于 250ms"的目标,让你可以将可靠性作为可衡量的承诺进行跟踪。这暗示了一个更大的方向。
搜索分析数据如何流入 Elastic?
数据流非常直接:

-
浏览器:用户进行搜索和点击。前端可以直接通过 OTel 发送事件,或者通过后端中转它们。
-
后端:你的搜索 API,通过 OTel 添加监测。每个搜索请求都会成为一个 span,并包含类似
search.query、search.result_count和search.query_id的 attributes。 -
Elastic(mOTLP):通过 mOTLP 端点接收和存储 OTel 追踪数据。将
OTEL_EXPORTER_OTLP_ENDPOINT指向你的 Elastic 部署,并使用ApiKey进行身份验证。这不需要收集器或转换。 -
Kibana:用于探索和可视化你的数据。在 Discover 中使用 ES|QL 运行临时查询,使用 APM UI 检查单个追踪,构建用于持续监测的仪表板,并在指标下降时设置告警。
OTel attributes 如何变成可查询的数据
在进行查询之前,你需要了解 Elastic 如何存储这些 OTel attributes,因为这会影响你编写 ES|QL 的方式。
通过原生 OTel 摄取,自定义 attributes 会直接存储在 attributes.* 下,并保留它们原始的点号表示法。不会进行下划线转换,也不会进行类型拆分,字符串、数字和布尔值都位于同一个命名空间中。
| OTel 属性 | 类别 | ES|QL 字段 |
|---|---|---|
| search.query | string | attributes.search.query |
| search.result_count | number | attributes.search.result_count |
| search.first_click | boolean | attributes.search.first_click |
这个映射正如它看起来一样简单:你的代码中的 attribute 名称就是查询中的字段名称。我们将在下一篇文章中介绍更多示例,届时你将亲自编写查询。
ES|QL:五行代码中的搜索数据
ES|QL 是 Elasticsearch 的管道式查询语言。你从一个数据源开始,然后一步一步地通过管道将它传递经过过滤器、聚合和计算。
下面是一个计算你的 CTR 的单个查询,即产生至少一次点击的搜索所占的百分比:
ini
`
1. FROM traces-generic.otel-default
2. | WHERE (name == "search" AND attributes.search.query IS NOT NULL)
3. OR attributes.search.first_click == true
4. | STATS
5. searches = COUNT(CASE(name == "search" AND attributes.search.query IS NOT NULL, 1)),
6. clicked = COUNT(CASE(attributes.search.first_click == true, 1))
7. | EVAL ctr_pct = ROUND(100.0 * clicked / searches, 1)
`AI写代码
从上到下阅读:从 traces-generic.otel-default 获取所有搜索 spans 和首次点击 spans,使用 COUNT(CASE(...)) 分别计算每种类型,然后进行除法计算得到 CTR。我们在监测时使用 search.first_click 标记每次搜索中的首次点击,因此查询只需要进行计数,无需进行 去重。一个查询提供一个计数结果,从而得到 CTR。
这就是这种模式。ES|QL 从上到下读取数据,每个管道步骤都会转换数据。在下一篇文章中,我们将针对真实数据运行六个这样的查询,包括热门查询、零结果分析、搜索性能和随时间变化的数量分析。敬请期待!
从搜索分析到全栈可观测性
通过选择 OTel 和 Elastic 进行搜索分析,你正在投资一种可以满足多种需求的基础设施。
计算 CTR 的相同追踪数据,也可以为你提供运营可见性,而无需额外的监测:

搜索仪表板的 SLO 卡片跟踪三个目标:你的搜索 延迟 目标(99% 低于 250ms)、搜索质量(85% 返回结果)以及可用性(99.9% 成功率)。在它们下面,延迟百分位数使用相同的基于数值的着色方式。绿色表示 健康 ,黄色表示 需要关注 ,红色表示 需要处理。
运营图表会分解时间消耗的位置(Elasticsearch 查询时间与应用程序开销之间的对比),以及延迟如何随时间变化。所有这些都来自你为分析添加的相同 search.* attributes,并且不需要额外的监测。
这就是 OTel 方法的实际优势:
-
搜索延迟:查询需要多长时间?哪些查询较慢?
-
错误率:搜索是否失败?如果失败,原因是什么?
-
依赖关系:Elasticsearch 性能如何影响你的搜索 API?
-
SLO:为搜索延迟或零结果率设置目标。
-
告警:在指标下降时获得通知。
-
异常检测:让机器学习(ML)发现搜索行为中的异常模式。
从搜索分析开始,你可以将这个基础扩展到全栈可观测性。这是一次监测投入,可以带来多种回报。
搜索分析需要哪些 OTel attributes?
要开始使用,你需要在搜索 spans 上捕获一些关键 attributes:
| Attribute | 类型 | 用途 |
|---|---|---|
search.query |
字符串 | 用户的搜索词 |
search.result_count |
数字 | 返回了多少结果(0 = 零结果搜索) |
search.query_id |
字符串 | 唯一查询标识符(由 trace ID 派生) |
search.result_click_id |
字符串 | 哪个结果被点击 |
search.result_click_position |
数字 | 被点击结果的位置(从 1 开始索引) |
对于点击追踪,将这些 attributes 添加到点击事件 spans 中:
| Attribute | 类型 | 用途 |
|---|---|---|
search.result_click_id |
字符串 | 被点击的文档 ID |
search.result_click_position |
数字 | 结果中的位置(从 1 开始索引) |
search.action |
字符串 | 事件类型:click、impression、add_to_cart、purchase |
search.query_id |
字符串 | 将此交互关联回原始搜索 |
search.first_click |
布尔值 | 每次搜索中的首次点击为 true(用于无需去重的 CTR) |
我们使用 search.* 命名空间,遵循 OTel 的领域特定前缀约定(http.*、db.*、messaging.*)。虽然 OTel 目前还没有标准化的搜索约定,但 search.* 是自描述的,并且与供应商无关。我们的命名参考了 User Behavior Insights (UBI) 标准,该标准定义了搜索事件的详细架构。我们参考它的事件结构,但不会让我们的监测与其绑定。
如果你还没有设置 APM,你可以将相同的 search.* attributes 作为 OTel 日志记录进行捕获,而不是 spans。分析概念完全相同;你只需要查询 logs-generic.otel-default,而不是 traces-generic.otel-default,并且 attributes.* 字段路径保持一致。有关设置详情,请参阅 OpenTelemetry logs with Elastic 文档。
这个搜索分析系列接下来会讲什么
本文介绍了使用 OTel 监测和 ES|QL 查询在 Elastic 上构建搜索分析的概念。本系列的其余部分将从概念深入到生产实践。敬请期待!
开始在 Elastic 上使用搜索分析
准备好将搜索分析添加到你的应用程序了吗?
-
参考项目:克隆、配置,并在 10 分钟内让搜索分析开始流入。
-
OpenTelemetry 和 Elastic:如何通过托管 OTLP 端点将 OTel 数据发送到 Elastic。
-
ES|QL 文档:学习查询语言。
-
Elastic Observability:更广泛的平台。
这是关于使用 OpenTelemetry 和 Elastic 进行搜索分析的六篇系列文章中的第一篇。下一篇:监测你的搜索 API:向你的后端添加搜索 attributes,并运行你的第一个 ES|QL 查询。
原文:Search analytics with OpenTelemetry and ES|QL - Elasticsearch Labs