【后端面试题】【中间件】【NoSQL】ElasticSearch面试基本思路和高可用方案(限流、消息队列、协调节点、双集群)

基本思路

业务开发面试Elasticsearch的时候基本问的是基础知识以及倒排索引。

Elasticsearch最基本的可用性保障就是分片,而且是主从分片,所以遇到Elasticsearch如何做到高可用这个问题的时候,首先要提到这一点。

Elasticsearch高可用的核心是分片,而且每个分片都有主从之分。如果主分片崩溃了,还可以使用从分片,从而保证最基本的可用性。

接着要补充Translog的作用

而且Elasticsearch在写入数据的时候,为了保证高性能,都是写到自己的Buffer里,后面再刷新到磁盘上。为了降低数据丢失的风险,Elasticsearch还额外写了一个Translog,类似MySQL的redo log,如果Elasticsearch崩溃的话,可以利用Translog来恢复数据。

接着尝试把话题引导到准备的高可用方案中

我维护的业务对可用性要求比较高,所以在Elasticsearch的基础上,还做了一些额外的优化,来保证Elasticsearch的高可用

Elasticsearch高可用方案

限流保护节点

限流是一个治标的策略,但是它能够保证Elasticsearch不会因为突发大流量而直接崩溃。

可以通过Elasticsearch的插件机制来实现自定义的限流策略,注意Elasticsearch集群本身提供了限流 的功能,也可以通过控制线程池大小和队列大小来间接实现限流的功能。

如果打算利用插件来实现限流功能的时候,就一定能够要有特殊之处。比如可以考虑结合Elasticsearch的内存使用率和CPU使用率设计限流策略。

之前用Elasticsearch的插件机制,设计过一个限流插件。功能比较简单,根据Elasticsearch当前的内存使用率和CPU使用率来判断是否需要执行限流。不管是内存使用率还是CPU使用率,只要超过阈值一段时间,就触发限流。

这里面试官也会考察怎么确定限流的阈值,超过阈值多少才会触发限流,限流之后怎么恢复等问题。

当然,如果你会研发限流插件,你也可以用插件来实现熔断、降级。熔断比较好处理,就是直接拒绝新的查询请求,但是降级这个就要考虑怎么降级了。如果你能够知道不同查询的业务价值,那么你就可以考虑触发降级的时候优先保障核心业务的请求,但是把非核心的请求拒绝了。总而言之,你之前在微服务学习到的熔断、限流、降级的思想,在这里一样适用。

如果你从来没有研发过 Elasticsearch 插件,那么也可以考虑其他两种策略,一种是在 Elasticsearch 之前加一个网关,查询经过网关的时候会被限流、熔断或者降级 。当然,引代理 也可以。

目前市面上这方面的产品不多,比较成熟的是极限网关,可以用一种自己了解但是没有实践过的话术说。

我还了解过Elasticsearch网关或代理,希望能够借助这些产品来做Elasticsearch的治理。比如借助网关做熔断、限流、降级这些,但是市面上相关的产品较少,也担心引入网关后的性能损耗,所以最后并没有实施这个方案。

另一种是在客户端这边限流各个业务方需要限制住自己的查询频率,防止把整个Elasticsearch打崩。相比之下,这种方式是最好落地的。

为了保护Elasticsearch,在客户端这边做了限流。比如某个业务的查询都比较慢,对Elasticsearch的压力很大,那么限流的阈值就比较小。

不过 Elasticsearch 设计之初就是为了支持高并发大数据的,所以最佳方式还是要考虑扩容

不管如何,限流都只能算是治标。如果经常触发限流,或者发现 Elasticsearch 有性能问题,那么还是要及时扩容的。

利用消息队列

在一些对数据实时性要求不高 的场景下,完全可以考虑在业务方和Elasticsearch中加入一个消息队列。可以抓住关键字 削峰和限流来回答。

之前优化过我们业务的架构,在数据同步到Elasticsearch之前,加入一个消息队列来削峰。在早期的时候,我们都是双写,一方面写数据库,一方面写Elasticsearch,在业务高峰期,Elasticsearch就会有性能瓶颈。

而实际上,我们业务对实时性的要求不高,在这种情况下,引入了消息队列。业务方只是写入数据库就返回,监听binlog并生成消息丢到kafka上。在这种情况下,如果Elasticsearch空闲的话,消费速率就高;如果Elasticsearch性能比较差,消费就比较慢,这样起到削峰和限流的效果

在这个架构的基础上,还可以考虑引入降级,也就是在 Elasticsearch 真的有性能问题的时候,关闭一部分消费者。

在这个架构的基础上,还做了一个简单的降级。如果有两类消费者写入数据到Elasticsearch,一类是核心数据消费者,一类是非核心数据消费者。

如果我监控到Elasticsearch性能已经比较差了,比如说写入的时候会遇到超时问题,就会把非核心数据消费者停下来。等Elasticsearch恢复过来再启动。

如果在大促或秒杀这种活动中,可以把整个数据同步都停掉,让Elasticsearch只支持查询操作。如果业务是电商类的,可以考虑这个策略。

保护协调节点

在Elasticsearch里,比较容易出问题的还有协调节点。协调节点类似分库分表代理,负责分发请求,处理结果集。如果一个查询需要消耗非常多的资源,就有可能把协调节点搞崩溃。如果有一个查询命中了10个分片,并且每个分片都返回了几万条数据,协调节点本身的资源使用量一下就会上去,甚至出现CPU100%或OOM问题。

因此要保证Elasticsearch高可用就要考虑防止突发大请求打崩协调节点问题。

整个面试思路是层层递进的。首先你可以指出如果公司内部资源比较多,那么可以考虑部署纯粹的协调节点

要想提高 Elasticsearch 的可用性,就要想办法防止协调节点在遇到大请求的时候崩溃。最简单的做法就是使用纯粹的协调节点。比如说专门部署一批节点,只扮演协调节点的角色。

接着可以补充怎么用好这些协调节点,关键词就是隔离

如果整个Elasticsearch除了这种纯粹的协调节点,还有一些兼任多个角色的协调节点,那么就可以考虑使用隔离策略。也就是说,如果客户端能够判定自己是大请求,就将请求发送到纯粹的协调节点上,否则发送到其他兼任的协调节点上。

这种做法的好处就是,大请求即使把协调节点打崩了,也只会影响到其他大请求。但是占据绝大多数的普通请求,并不会受到影响。

这种做法的好处是和隔离结合在了一起,因此你可以尝试把话题引导到隔离策略上。在一些技术实力很强的大厂,它们还会对 Elasticsearch 进行二次开发。可以修改协调节点的逻辑,让协调节点在资源快不足的时候,直接拒绝这种大请求。如果你在大厂,可以了解一下自己公司有没有在这方面做优化。

你可以在这个基础上进一步总结,就是只使用单一角色的节点以提高可用性

在资源足够的情况下,我是建议所有的节点都只扮演单一角色。这样做不仅仅能够带来可用性的提升,也能带来性能的提升。

双集群

双集群算是一个很高级、投入也很大的高可用方案。

最简单的方案就是直接使用付费的CCR跨集群复制,面试的时候简单提一下就可以。

提高 Elasticsearch 可用性还有一个方法,就是使用双集群。比如说直接使用付费的 CCR 功能,不过我司比较穷,肯定是不愿意买的。

在不使用这种付费功能的情况下,就只能考虑自己做了。这里有一个比较简单的方案,假如说有 A 和 B 两个集群,那么基本思路就是这样的:

  • 使用消息队列来保持双写

  • 在查询的时候,优先使用 A 集群,当确认 A 集群出了问题的时候,切换到 B 集群。

抓住关键词消息队列双写回答。

我们采用的是一个比较简单的双集群方案。就是写入的时候并不是直接写入到 Elasticsearch,而是写入到消息队列,而后启动两个消费者,分别消费消息,然后写到两个集群 AB 里面。关键在于查询的时候,要判断集群 A 有没有出问题,出了问题就切换到集群 B。

而怎么判断集群 A 是否已经出问题,可以参考微服务中判断节点是否健康的部分,思路都是类似的。

具体怎么切换,有两种思路。一种是你使用的客户端切换,一种是利用 DNS 机制切换。也就是说,正常情况下,你使用的 Elasticsearch 的连接信息,DNS 解析的时候返回的是集群 A 的 IP。但是当触发了容灾切换的时候,DNS 解析得到的是集群 B 的地址。

你在回答的时候可以选择其中任意一种,这里我以客户端为例来说一说。

为了实现自动切换的效果,我们对 Elasticsearch 的客户端进行了二次封装。在封装之后,正常情况下,会访问集群 A。同时客户端监控集群 A 的响应时间。如果响应时间超出预期,又或者返回了比较多超时响应,客户端就会自动切换到集群 B 上。

相关推荐
一起努力啊~3 分钟前
算法刷题--哈希表
算法·面试·散列表
Libby博仙6 分钟前
Spring Boot 条件化注解深度解析
java·spring boot·后端
源代码•宸24 分钟前
Golang原理剖析(Map 源码梳理)
经验分享·后端·算法·leetcode·golang·map
小周在成长27 分钟前
动态SQL与MyBatis动态SQL最佳实践
后端
瓦尔登湖懒羊羊36 分钟前
TCP的自我介绍
后端
小周在成长38 分钟前
MyBatis 动态SQL学习
后端
子非鱼92141 分钟前
SpringBoot快速上手
java·spring boot·后端
我爱娃哈哈1 小时前
SpringBoot + XXL-JOB + Quartz:任务调度双引擎选型与高可用调度平台搭建
java·spring boot·后端
JavaGuide1 小时前
Maven 4 终于快来了,新特性很香!
后端·maven
开心就好20251 小时前
全面解析iOS应用代码混淆和加密加固方法与实践注意事项
后端