上篇介绍了 CPU、内存、磁盘等基础设施监控,本篇深入索引层面——线程池、分片分布、查询性能、段合并,帮你快速定位性能瓶颈。
为什么要监控索引性能指标?
基础设施健康不代表业务正常,索引层面的问题往往更隐蔽:
- 线程池队列堆积 → 请求被拒绝,用户报错
- 分片分布不均 → 热点节点,负载倾斜
- 查询性能下降 → 响应变慢,用户投诉
- 段合并频繁 → 写入吞吐量下降
这些问题在 CPU、内存指标上可能看不出来,需要专门的索引监控。
线程池监控:发现队列堆积
线程池是 Easysearch 处理请求的核心,队列堆积或拒绝是性能问题的早期信号:
1 | GET _cat/thread_pool?v&h=node_name,name,active,queue,rejected,type |
1 | node_name name active queue rejected type |
重点关注这几个线程池:
| 线程池 | 作用 | 告警建议 |
|---|---|---|
| search | 处理搜索请求 | queue 持续增长 或 rejected > 0 |
| write | 处理写入请求 | queue 持续增长 或 rejected > 0 |
| get | 处理 GET 请求 | rejected > 0 |
| force_merge | 段合并操作 | active 长时间 > 0 需关注 |
💡 关于告警阈值:建议先观察集群正常运行时的基线,再根据实际情况设置告警。关键是关注 rejected > 0(请求被拒绝)和 queue 持续增长(处理能力跟不上)。
查看线程池配置:
1 | # 查看默认配置 |
1 | { |
1 | # 查看节点实际配置 |
1 | { |
💡 两个 API 的区别:
_cluster/settings返回集群级别的默认配置,_nodes/thread_pool返回每个节点的实际运行配置(包含 type 信息)。
Easysearch 主要线程池默认配置:
| 线程池 | 类型 | size | queue_size | 说明 |
|---|---|---|---|---|
| search | fixed_auto_queue_size | 16 | 1000 | 处理搜索请求 |
| write | fixed | 10 | 10000 | 处理写入请求 |
| get | fixed | 10 | 1000 | 处理 GET 请求 |
| analyze | fixed | 8 | 256 | 文本分析 |
| management | scaling | 1-5 | -1 | 集群管理任务 |
| flush | scaling | 1-5 | -1 | 刷新到磁盘 |
| refresh | scaling | 1-5 | -1 | 刷新索引 |
| force_merge | fixed | 1 | -1 | 段合并 |
| snapshot | scaling | 1-5 | -1 | 快照操作 |
| sql-worker | fixed | 10 | 1000 | SQL 查询 |
| ai | scaling | 0-10 | -1 | AI 功能 |
💡
queue_size = -1表示无界队列(scaling 类型线程池的特点)。size列中1-5表示 scaling 类型的 core 到 max 范围。
当前集群解读:
| 线程池 | active | queue | rejected | 状态 |
|---|---|---|---|---|
| search | 0 | 0 | 0 | ✅ 空闲 |
| write | 0 | 0 | 0 | ✅ 空闲 |
| management | 1 | 0 | 0 | ✅ 正常 |
| 其他 | 0 | 0 | 0 | ✅ 空闲 |
所有线程池都很健康,没有队列堆积,没有请求被拒绝。说明当前负载很轻,集群处理能力充足。
⚠️ rejected 不为 0 说明请求被拒绝了,这是严重问题,需要立即排查是资源不足还是请求量过大。
索引级别监控:定位问题索引
集群整体健康不代表每个索引都正常,单独检查索引状态很有必要:
1 | # 查看所有索引,手动筛选异常状态 |
1 | health status index uuid pri rep docs.count docs.deleted store.size pri.store.size |
上面的结果显示有多个 yellow 状态的索引,原因是它们配置了 1 个副本(rep=1),但当前是单节点集群,副本无法分配到其他节点。系统索引(以 . 开头)如 .security 和 .analysis_ik 配置为 0 副本,所以是 green 状态。
1 | # 按大小排序,找出最大的索引 |
💡 示例输出(生产环境可能看到类似这样的大索引):
1 | index health pri rep docs.count store.size |
索引健康检查清单:
| 检查项 | 命令 | 说明 |
|---|---|---|
| 异常状态索引 | _cat/indices?v&health=yellow | 应该为空 |
| 超大索引 | _cat/indices?s=store.size:desc | 单个索引建议 < 50GB |
| 文档数异常 | _cat/indices?s=docs.count:desc | 对比历史数据 |
分片分布监控:避免热点节点
分片分布不均会导致某些节点负载过高:
1 | GET _cat/shards?v&s=store:desc&h=index,shard,prirep,state,docs,store,node |
💡 示例输出(生产环境可能看到类似这样的分片分布):
1 | index shard prirep state docs store node |
1 | # 查看每个节点的分片数量 |
1 | shards disk.indices disk.used disk.avail disk.total disk.percent host ip node |
💡 关于 UNASSIGNED 分片:上面显示有 5 个未分配的分片,这是因为
test-load、products以及 ILM 相关索引配置了 1 个副本,但当前是单节点集群,副本无法分配到其他节点。这在单节点测试环境是正常的。
分片分布健康指标:
| 指标 | 健康标准 |
|---|---|
| 节点间分片数差异 | < 20% |
| 单节点最大分片数 | < 1000 |
| UNASSIGNED 分片 | 应为 0 |
💡 小贴士:如果发现分片分布不均,可以用
POST _cluster/reroute手动调整,或调整cluster.routing.allocation相关配置。
查询性能监控:定位慢查询
搜索变慢是最常见的用户投诉,这些指标帮你快速定位:
1 | GET _nodes/stats/indices/search |
1 | { |
关键性能指标计算:
1 | 平均查询耗时 = query_time_in_millis / query_total |
| 指标 | 计算方式 | 健康阈值 |
|---|---|---|
| 平均查询耗时 | query_time / query_total | < 100ms |
| 平均 fetch 耗时 | fetch_time / fetch_total | < 50ms |
| 当前查询数 | query_current | 持续 > 10 需关注 |
| scroll 上下文 | scroll_current | 持续增长需关注 |
当前集群解读:
| 指标 | 当前值 | 状态 |
|---|---|---|
| 总查询次数 | 395 次 | - |
| 平均查询耗时 | 0.95ms | ✅ 非常快 |
| 平均 fetch 耗时 | 0.22ms | ✅ 非常快 |
| 当前进行中查询 | 0 | ✅ 无积压 |
| scroll 上下文 | 0 | ✅ 无泄漏 |
| scroll 总耗时 | 708s | ⚠️ 历史 scroll 查询较多 |
查询性能非常优秀,平均响应时间在毫秒级,远低于 100ms 的健康阈值。scroll_time 较高是因为之前执行过多次 scroll 查询测试。
⚠️ 如果平均查询耗时突然上升,检查:1) 是否有复杂聚合查询 2) 是否在做段合并 3) 堆内存是否不足
段合并监控:写入性能的隐形杀手
段(Segment)合并是 Lucene 的核心机制,但频繁合并会严重影响写入性能:
1 | GET _nodes/stats/indices/merges |
1 | { |
段合并健康指标:
| 指标 | 说明 | 关注点 |
|---|---|---|
| current | 当前正在进行的合并数 | 持续 > 0 说明合并压力大 |
| total_throttled_time | 被限流的时间 | > 0 说明磁盘 I/O 跟不上 |
| total_stopped_time | 被停止的时间 | > 0 需要排查原因 |
当前集群解读:
| 指标 | 当前值 | 状态 |
|---|---|---|
| 当前合并数 | 0 | ✅ 无合并进行中 |
| 历史合并次数 | 3 次 | ✅ 正常 |
| 合并总耗时 | 49ms | ✅ 合并开销很小 |
| 合并文档数 | 18 个 | ✅ 小规模合并 |
| 被限流时间 | 0 | ✅ I/O 无压力 |
| 被停止时间 | 0 | ✅ 正常 |
段合并状态健康,当前集群数据量较小(135 个文档),已完成 3 次小规模段合并,总耗时仅 49ms。
1 | # 查看每个索引的段数量 |
💡 优化建议:
- 如果段合并频繁,考虑增大
index.refresh_interval(默认 1s)- 批量写入时可以临时设置
refresh_interval: -1- 单个分片的段数量建议控制在 50 个以内
监控告警建议
根据实践经验,建议设置以下告警阈值:
| 指标 | ⚠️ 警告 | 🔴 严重 |
|---|---|---|
| search 线程池 queue | 持续增长 | rejected > 0 |
| write 线程池 queue | 持续增长 | rejected > 0 |
| 线程池 rejected | > 0 | 持续 > 0 |
| 平均查询耗时 | > 100ms | > 500ms |
| 当前合并数 | 持续 > 2 | 持续 > 5 |
| 索引状态 | yellow | red |
常用命令速查表
1 | # 🧵 线程池状态 |
使用 MCP 工具自动化监控
如果你使用 AI Agent(如 Kiro、Claude Desktop),可以通过 Easysearch MCP Server 让 AI 直接操作集群,实现自然语言监控:
配置 MCP 客户端 (.kiro/settings/mcp.json):
1 | { |
自然语言监控示例:
| 你说 | AI 调用的 MCP 工具 |
|---|---|
| “查看线程池状态” | cat_thread_pool() |
| “哪些索引是 yellow 状态” | cat_indices(health="yellow") |
| “查看分片分布” | cat_shards() |
| “查询性能怎么样” | nodes_stats(metric="indices") |
| “有没有段合并在进行” | nodes_stats(metric="indices") |
| “磁盘使用情况” | cat_allocation() |
MCP Server 提供 121 个工具,覆盖集群管理、索引操作、搜索查询、监控诊断等全部功能,让 AI 成为你的 Easysearch 运维助手。
总结
监控 Easysearch 集群的索引性能,掌握这几个核心 API 就够了:
_cat/thread_pool- 线程池队列_cat/indices- 索引健康_cat/shards- 分片分布_nodes/stats/indices/search- 查询性能_nodes/stats/indices/merges- 段合并状态
结合上篇的基础设施监控,你就拥有了完整的 Easysearch 集群监控体系。
Easysearch 完全兼容 Elasticsearch/OpenSearch API,如果你之前用过这些产品,可以无缝迁移。
参考文档:

