一、宏观设置

  1. 注意CPU核数,CPU的核数将影响Thread Pool,也就是和检索与索引的线程池有关,建议CPU在16核+;
  2. 根据需要设置索引和type,因为高版本(6.0+)index里面只能有一个type,所以建议在低版本里面即采用这一设定,并且这里也要考虑到版本迭代里面的父子文档。
  3. 合理设置分片和副本,分片一般大于等于节点数,副本根据需要进行设置,分片容量一般不要大于30GB。
  4. 冷热数据分离

二、索引优化

  1. 牺牲近实时搜索,修改refresh的时间。一般情况下refresh_interval设置为1s,表示1秒后即可搜索。如果设置时间长,或者-1(-1表示关闭自动刷新),可以优化索引。
  2. 减少副本,在索引前将副本设置为0,生成后将其还原。
  3. 能批量就不要单条插入,尽量多使用bulk。

三、搜索优化

  1. 少用wildcard进行查询,TB+的数据上,很容易卡死。
  2. 中文使用match匹配是不准确的,使用matchPhrace短语匹配更加准确,其实使用term的查询代价更小,只是对于中文搜索不太准确。
  3. 如果该字段不需要计算相关度评分,使用filter更加迅速。
    query和Filter对比:
    query是有两个操作:查询和计算相关度,而filter是仅仅是判断是否满足条件,并且Es会自动缓存过滤器的内容。

过滤上下文是在使用filter参数时候的执行环境,比如在bool查询中使用Must_not或者filter。

  1. 尽可能避免深度分页。
    深度分页的问题在于数据时存储在分片上的,也就是说查第100页的10条数据,必须在5个分页上查出前1000条的数据,将这些5000数据进行排序,取其前10条数据,可想而知,分页越往后效率越低。
    并且当 from + size > max_result_window (Es设置,默认10000)时,es 将返回错误。
  2. 聚合分页size的合理设置。Es处于性能考虑,不支持聚合分页。

方案一:每次取聚合结果,拿到内存中分页返回。
方案二:scroll结合scroll after集合redis实现。

  1. 不要使用脚本