Elasticsearch調優篇慢查詢分析筆記

NO IMAGE

前言

  • elasticsearch提供了非常靈活的搜索條件給我們使用,在使用複雜表達式的同時,如果使用不當,可能也會為我們帶來了潛在的風險,因為影響查詢性能的因素很多很多,這篇筆記主要記錄一下慢查詢可能的原因,及其優化的方向。
  • 本文討論的es版本為7.0+。

慢查詢現象

查詢服務超時
  • 最直觀的現象就是提供查詢的服務響應超時。
大量連接被拒絕

Elasticsearch調優篇慢查詢分析筆記

  • 我們有時候寫查詢,為了圖方遍,經常使用通配符*來查詢,這有可能會匹配到多個索引,由於索引下分片太多,超過了集群中的核心數。就會在搜索線程池中造成排隊任務,從而導致搜索拒絕。
查詢延遲

主機CPU飆高
  • 另一個常見原因是磁盤 I/O 速度慢,導致搜索排隊或在某些情況下 CPU 完全飽和。
  • 除了文件系統緩存,Elasticsearch 還使用查詢緩存和請求緩存來提高搜索速度。 所有這些緩存都可以使用搜索請求進行優化,以便每次都將某些搜索請求路由到同一組分片,而不是在不同的可用副本之間進行交替。這將更好地利用請求緩存、節點查詢緩存和文件系統緩存。Es默認會在內存使用75%時發生FullGC ,做好主機和節點的監控同樣重要。

Elasticsearch調優篇慢查詢分析筆記

Elasticsearch調優篇慢查詢分析筆記

優化方法

根據查詢時間段動態計算索引

  • elasticsearch支持同時查詢多個索引,為了提高查詢效率,避免使用通配符查詢,我們可以計算枚舉出所有的目標索引,一般es的數據都是按時間分索引,我們可以根據前端傳入的時間段,計算出目標索引。
控制分片數量
  • 分片的數量和節點和內存有一定的關係。
  • 最理想的分片數量應該依賴於節點的數量。 數量是節點數量的1.5到3倍。
  • 每個節點上可以存儲的分片數量,和堆內存成正比。官方推薦:1GB 的內存,分片配置最好不要超過20。
注意from/to查詢帶來的深度分頁問題

  • 舉例假如每頁為 10 條數據,你現在要查詢第 200 頁,實際上是會把每個 Shard 上存儲的前 2000條數據都查到一個協調節點上。
    如果你有 5 個 分片,那麼就有 10000 條數據,接著協調節點對這 10000 條數據進行一些合併、處理,再獲取到最終第 200 頁的 10 條數據。實在需要查詢很多數據,可以使用scroll API 滾動查詢。
為你的索引配置索引模板
  • 在低版本的es中默認的分片是5個,在高版本中改成了1,我們需要根據索引的索引量來動態調整分片數量,這裡推薦設置一個默認匹配規則,將優先級設置高一些(ps:order高的會覆蓋order低的模板),避免查詢掃描過多的分片,合理利用集群資源。

Elasticsearch調優篇慢查詢分析筆記

避免數據分桶太多

對於分桶數量太大的聚合請求,應該將所有數據切片,比如按時間分片,多次請求,來提高查詢效率,並且避免內存OOM。

獨立協調節點
  • 集群中應該有獨立的協調節點,專門用於數據請求(node.master=false node.data=false),並給它們設置足夠的內存。通過數據節點與協調節點分離,可以避免節點掛掉之後,導致整個集群不可用,或者長時間響應遲鈍。
Routing數據路由

適當的增加刷新間隔
  • es是一個準實時的搜索框架,這就意味著,從索引一個文檔直到文檔能夠被搜索到有一個輕微的延遲,也就是 index.refresh_ interval ,默認值是1秒,適當的增加這個值,可以避免創建過多的segment(segment是最小的檢索單元)。
配置慢查詢日誌
  • 通過在 Elasticsearch 中啟用 slowlogs 來識別運行緩慢的查詢。slowlogs 專門用於分片級別,僅適用於數據節點。協調/客戶端節點不具備慢日誌分析功能,因為它們不保存數據。通過它,我們可以在日誌中看到,那個查詢語句耗時長,從而制定優化措施。
index.search.slowlog.threshold.query.warn: 10s
index.search.slowlog.threshold.query.info: 5s
index.search.slowlog.threshold.query.debug: 2s
index.search.slowlog.threshold.query.trace: 500ms
index.search.slowlog.threshold.fetch.warn: 1s
index.search.slowlog.threshold.fetch.info: 800ms
index.search.slowlog.threshold.fetch.debug: 500ms
index.search.slowlog.threshold.fetch.trace: 200ms
index.search.slowlog.level: info
配置熔斷策略
  • es7.0後版本提供一系列的斷路器,用於防止操作引起OutOfMemoryError。每個斷路器都指定了可以使用多少內存的限制。此外,還有一個父級斷路器,用於指定可在所有斷路器上使用的內存總量。

indices.breaker.request.limit:請求中斷的限制,默認為JVM堆的60%。

indices.breaker.total.limit:總體父中斷程序的啟動限制,如果indices.breaker.total.userealmemory為,則默認為JVM堆的70% false。如果indices.breaker.total.userealmemory 為true,則默認為JVM堆的95%。

network.breaker.inflight requests.limit 限制當前通過HTTP等進來的請求使用內存不能超過Node內存的指定值。這個內存主要是限制請求內容的長度。 默認100%。

script.maxcompilationsrate:在允許的時間間隔內限制動態腳本的併發執行數量。默認值為75 / 5m,即每5分鐘75。

歡迎來公眾號【俠夢的開發筆記】 一起交流進步

相關文章

GoWeb編程之模板(一)

Kotlin系列之函數的定義與調用

Scala教程之:可變和不變集合

Hadoop完全分佈式安裝與部署