说说你们公司 es 的集群架构,索引数据大小,分片有多少
2026/5/12大约 5 分钟面试题面试题
一、 标准面试回答模版(建议背诵)
面试官: 说说你们公司 ES 的集群架构,索引数据大小,分片有多少?依据是什么?
Fox版标准回答:
“关于 ES 架构,我不是拍脑袋定的,而是根据业务增量、机器成本和架构演进三个维度来规划的。以我们核心的 ELK 日志平台为例:
- 容量与分片规划(算账):
- 数据量: 我们的日增量是 1TB。考虑到保留 7 天和 1 副本(1 Replica),总数据量约 14TB。我申请了 10 台 Data 节点(每台挂载 4TB NVMe SSD),预留了 40% 的水位线给突发流量和段合并(Segment Merge)。
- 分片数: 依据单主分片 30GB-50GB 的业内黄金法则,我将每日索引的主分片数设置为 24。
- 计算逻辑:1024GB/ 24 = 42GB,这个大小既保证了写入并发能力,又避免了分片过大导致故障恢复慢的问题。
- 物理与逻辑架构(部署):
角色分离: 我们采用了 13+2 的架构。
3 台专用 Master: 低配(4核8G),跨可用区(Zone)部署,核心目的是防止脑裂,保证集群大脑的高可用。
10 台 Data 节点: 高配(16核64G),负责数据存储和写入。
2 台协调节点(Coordinating Node): 针对部分重度聚合查询,我独立部署了协调节点,专门做 Scatter-Gather(分发与汇聚),实现了计算与存储的分离,防止复杂查询 OOM 搞挂数据节点。
- 关键参数调优(亮点):
- 内存陷阱: Data 节点虽有 64G 内存,但我将 JVM 堆内存严格锁定在 31GB,是为了利用 JVM 的指针压缩(Compressed Oops)技术。剩余 33G 全部留给操作系统的 Page Cache,加速 Lucene 的倒排索引查询。
- 写入优化: 针对日志写多读少的特点,我将
refresh_interval调大到 30s,并将 Translog 设置为异步落盘,用极小的可见性延迟换取了写入性能的翻倍。”
二、 原理与数据结构层面的体现
1. 场景一:为什么要卡在 31GB 内存?—— 指针压缩(Compressed Oops)
- 场景: 公司配了 64GB 甚至 128GB 的大内存机器,新手往往会把堆内存设为 48GB 或更多。
- 问题: Java 对象头中的指针通常是 64 位的。当堆内存 < 32GB 时,JVM 默认开启指针压缩,将指针压缩为 32 位。一旦跨过 32GB 这个阈值,指针被迫膨胀回 64 位。
- 后果: 内存占用瞬间变大,CPU 缓存命中率降低,性能不升反降。
- **ES 的解法:Heap 。
- 原理: 剩下的内存并没有浪费,而是给到了 OS Page Cache。ES 底层 Lucene 的 Segment 文件主要存储在磁盘,极其依赖 Page Cache 进行缓存加速。给堆内存留空间不如给系统缓存留空间。
2. 场景二:分片为什么不能太小或太大?—— 元数据开销 vs I/O 瓶颈
- 场景: 1TB 数据,有人分 1000 个片(太小),有人分 1 个片(太大)。
- 问题 A(太小): 分片(Shard)是 Lucene 的一个实例,有独立的开销。分片过多会导致 Cluster State(元数据)极其庞大,Master 节点在分发元数据时会卡顿甚至 OOM(Mapping Explosion)。
- 问题 B(太大): 单个分片超过 50GB。当发生故障迁移或 Segment Merge 时,巨大的文件会长时间占用磁盘 I/O 和网络带宽,导致集群“假死”。
- Fox 的解法:30GB - 50GB 黄金区间。这是在“元数据管理压力”和“数据恢复/合并压力”之间找到的最佳平衡点。
3. 场景三:磁盘 RAID 怎么做?—— 软件高可用 vs 硬件高性能
- 场景: 运维问你,Data 节点的磁盘做 RAID 5 还是 RAID 10?
- 问题: RAID 5 写入慢,RAID 10 成本高且空间减半。
- Fox 的解法:RAID 0。
- 原理: ES 应用层已经有了 Replica(副本)机制,数据安全由软件保证。硬件层我们要的是极致的 I/O 吞吐量和 100% 的磁盘利用率。
- 效果: 即使坏了一块盘,RAID 0 导致单机数据全丢,ES 集群也能通过副本机制在其他节点自动恢复(Rebalance),业务层无感知。
三、 Fox的深度解析
如果面试官追问:“如果业务突然变成电商商品搜索(读多写少),架构要怎么变?” 或者 “为什么要加协调节点?”
Fox版解析:
1. 关于“场景化调优”的辩证思维:
“面试官,架构没有银弹。刚才的配置是针对日志场景(写多读少)的。 如果是电商搜索(读多写少、低延迟),我会做反向调整:
- 分片策略: 我会把单分片压缩到 20GB 甚至更小。因为分片越小,在多节点并发查询时的并行度(Parallelism)越高,P99 延迟越低。
- 刷新策略:
refresh_interval调回 1s。因为商家改了价格,用户必须立刻看到,这时候实时性 > 写入吞吐量。 - Translog: 改回
request(同步刷盘),因为商品数据一条都不能丢。”
2. 关于“协调节点”的架构演进:
“我认为架构是演进出来的。
- 初期: Client 直连 Data 节点,省钱。
- 痛点: 随着聚合查询(Aggregation)变复杂,Data 节点既要负责 I/O(查硬盘),又要负责 Compute(内存排序归并)。一旦遇到大查询,Data 节点 OOM,写入也会跟着挂。
- 演进: 引入协调节点(Coordinating Node)。它不存数据,只做 Scatter-Gather。
- 价值: 这本质上是存储与计算分离的思想。把‘计算风险’隔离在协调节点,保住了‘数据底座’的稳定性。”