当前位置: 首页 > 科技观察

记得在ElasticSearch中避开这些坑

时间:2023-03-22 12:55:34 科技观察

1.管理方式ElasticSearch作为最常用的搜索引擎组件,在系统架构中扮演着极其重要的角色,可以大大提高数据加载和检索的效率;但不可否认的是,在长期的应用实践中,也发现有很多流程和场景难以处理;直观来说,索引在业务中的使用主要涉及如图所示的几个流程,其核心是索引结构维护和数据流管理两个模块;如果数据结构比较简单,体积小,那么可能比较好用;如果数据体复杂,会动态扩展,体积过大,很容易踩到一些坑;例如:一旦索引中的字段出错,调整过程非常复杂;数据流向索引的方式需要根据场景灵活选择;以及数据查询中深度分页的问题;下面将总结围绕这些问题的应对策略;顺便说一下,很多组件在应用的时候其实是用到了的。有不符合预期的地方,可以考虑在集成的时候写一个自定义的管理程序,解决使用过程中可能出现的问题;2.结构维护对于ES索引的结构维护,如果数据主体比较简单,可以考虑手动管理,但实际上在使用索引时,主体结构通常比较复杂,常见的有字段超过30-50个,需要流程化管理;结构映射:索引需要构建的主要结构,统一维护在字段库中。值得注意的是字段名和类型,字段可以和关系数据库的查询保持一致,但是不同组件类型的描述是不一样的,尤其是ES,如果字段类型不合理,会影响使用搜索;索引结构:在实际业务场景中,字段信息会动态变化,这会给索引结构的维护带来很多麻烦。字段的增减容易管理,但是如果涉及到类型的变化,就有一个重建索引的过程,会导致数据的多次重新调度,也是一个高风险的操作;程序维护:这种结构维护机制的核心目的是对整个过程进行程序化管理,避免人工干预,从而保证索引结构的稳定扩展;不得不提的一个教训是,在管理业务日志的索引结构时,发生了误删。留下几公分的影子,事后会把维修过程完全程式化,避免误动作,它的核心操作是读和写两个动作,但是为了让进程容错和稳定,通常需要设计策略和解决方案;同步双写:对数据的实时性要求极高,通常在一个事务中完成数据的双写动作,保证数据层面的强一致性;异步解耦:完成数据后库的写动作之后,基于MQ消息解耦索引的写,过程中有轻微的延迟。如果消费失败,数据会丢失;定时任务:通过任务调度,在指定时间段同步新数据的机制,存在明显的时效性问题;组件同步:使用合适的同步组件,比如官方组件或者一些第三方开源组件,原理和任务同步类似;数据同步的选项有很多,如何选择完全取决于具体的场景。在以往的使用过程中,核心业务会使用同步双写,内部活动业务会使用异步方式,业务日志会使用任务调度,系统监控或者执行日志都会用到。主要依赖同步组件;2.中断与恢复无论用什么方式将数据同步到索引,都不得不面对一个灵魂问题。如果进程突然异常中断,恢复后如何保证索引数据不丢失?这个问题适用于许多复杂的过程;容错性是衡量一个复杂过程的核心指标。比如在索引数据同步的过程中,需要有短暂的停顿,或者进程被迫中断时,恢复后应该能够自动修复索引。缺乏数据的能力;ES实践中很经典的一个问题。修改索引结构时需要重建索引。这时,必须将当前索引移动到临时索引中。索引结构调整完成后,需要从临时索引中移回。数据,在这个过程中,可以动态调整服务交互的索引名称;当然,你也可以直接使用临时索引作为交互索引,避免迁移动作。这个动态标识需要嵌入到服务中,并且在整个reindex过程中使用,应该避免人工干预。就个人而言,我仍然相信程序的安全性和准确性;4.刷新策略向ES索引写入数据时,有3种不同的数据刷新机制。看6.8版本的设置中,参数refresh_interval设置为1s,即写动作执行后1秒后可以查找数据,避免频繁写入,过多消耗资源;NONE:默认刷新策略,请求提交后,不会等待数据刷新,减少资源消耗但数据实时性低;IMMEDIATE:请求提交后立即刷新索引,数据实时性高但资源消耗过大,建议在API文档中测试;WAIT_UNTIL:请求提交后,会等待索引刷新后再结束,是比较平衡的策略;对于索引数据的维护,刷新机制主要体现在增删改查的动作上,直接影响到实时查询。至于如何选择,还是需要结合具体场景,尤其是与同步方案密切相关的策略,也可以在索引交互中动态维护策略,满足突发需求;5、深度分页对于数据查询,几乎总是有分页的需求。在常见的应用中,连续下拉功能有最大限制值;from/Size在ES中常用来进行分页查询,但是有一个限制,在索引设置中有一个max_result_window页面深度限制,6.8版本默认值为10000,即10000之后的数据不能使用From/Size翻转;首先分析一下实际的应用场景,大部分的翻页需求最多都在前10页左右,所以从这个角度来看,ES翻页被限制在一个合理的范围内。在实践中,一些指标也有所提高,目前还没有出现明显的问题。从技术角度思考,如果翻页参数太大,意味着更多的数据过滤,那么对计算资源的占用也会增加。ES引擎的强大在于它的搜索能力,只需要检索出符合要求的数据即可;无论是ES还是其他类似的分布式存储组件,甚至MySQL的分库分表模式,其本质都是将数据分布在不同服务节点的不同数据切片上;常规的执行原则是为请求分配一个主节点,协调各个节点执行同一个查询,完成结果汇总和响应。深度分页的计算资源占用自然很高;如果深度分页是绝对必要的,在6.8版本中还有另外两种方法,Scroll或Search-After。使用方法请参考相关文档。6.参考源码编程文档:https://gitee.com/cicadasmile/butte-java-note应用仓库:https://gitee.com/cicadasmile/butte-flyer-parent