1. 程式人生 > >elasticsearch 查詢優化建議

elasticsearch 查詢優化建議

最近在做一些索引相關的優化測試,順便記錄一下測試以及效果

1:優化mapping  主要包括  doc_values , index  , norms  , type的keyword和text  // 效果明顯

doc_values屬性  用於把資料序列化到磁碟,使索引結構更緊密

                預設為true,binary型別為false

                缺點:產生額外磁碟消耗

index 屬性 用於是否對資料索引,對於一些沒必要的資料不必要進行索引檢索

                預設都為true

                缺點:對與無索引的物件無法使用條件過濾和查詢

norms屬性

              不必要聚合的屬性可以設定為false


keyword和text是String的拓展,5X之後使用這兩個屬性

                keyword屬性為對資料不建倒排類似以前的String: { "index": "not_analyzed"},text為對資料進行分詞倒排

效果:能極大的減少磁碟空間

2 :  禁用 查詢中的 _all , 設定合理的shard分片數 ,使用segment段落合併  // 效果明顯

_all 預設開啟,會把所有欄位都在拷貝到這裡,增加磁碟使用和影響查詢效能

建立索引時新增 "_all":{"enabled":false}

shard

一個Shard就是一個Lucene例項,是一個完整的搜尋引擎。

分片數過多會導致檢索時開啟比較多的檔案,多臺伺服器之間通訊成本加大。

而分片數過少會導至單個分片索引過大,所以檢索速度也會慢。

建議單個分片最多儲存10G-20G左右的索引資料,每個例項的每個索引分片數建議在1-2個左右,並且儘量叢集的所有節點

都分片數一致,不要出現分片數不一樣導致的一個例項負載過大,等待合併的時間變長;

shard副本

使用副本的優點:資料備份,提高對大索引的查詢效率,建議副本在1-2個左右,過多的副本會延遲合併時間以及磁碟使用率提高,價效比不高

segments

每個分片包含多個segment,每一個segment都是一個倒排索引;在查詢的時,會把所有的segment查詢結果彙總歸併後最為最終的分片查詢結果返回; segment越多,載入到記憶體中的segment越多,佔用segment memory越多,查詢效能可能就會下降,因此應該合併小的segment,減小segment數,提高檢索的segment數來提高查詢效率

建立索引的時候,elasticsearch會把文件資訊寫到記憶體bugffer中,elasticsearch定期會執行flush操作,把segment持久化到磁碟上,索引越大,segment越多,查詢效率就會下降,由於segment建立是隻是寫入快取,這時期容易系統異常容易丟失資料,可手動執行_flush來實現段落持久化

---- 合併索引段落語句

curl -XPOST 'http://localhost:9200/{_index}/_forcemerge?max_num_segments=1'

----並且每個es例項不要超過32G的jvm記憶體

---------------------以上策略 能提高不少的查詢效率

3:避免記憶體交換 ,bootstrap.mlockall設定為true來實現  // 意義不大,或許是測試資料集1000w不夠大,無法實現

在elasticsearch.yml裡新增

bootstrap.memory_lock: true

    1./etc/security/limits.conf ,不限制Es啟動使用者(如xxx)的memlock
                xxx soft memlock unlimited
                xxx hard memlock unlimited
     2.修改:/etc/sysctl.conf

                vm.swappiness=0   

      ---------延遲重新整理時間或禁用重新整理
               curl -XGET 'localhost:9200/novehicle-new/_settings' -d '{"refresh_interval": -1}'

4 : 優化query,查詢的query返回必要欄位,不用的欄位,減小返回值大小     

5:優化日誌輸出等級,把trance改成info   // 好像效果不大

6: 路由優化  // 還在測試

ES中所謂的路由和IP網路不同,是一個類似於Tag的東西。在建立文件的時候,可以通過欄位為文件增加一個路由屬性的Tag。ES內在機制決定了擁有相同路由屬性的文件,一定會被分配到同一個分片上,無論是主分片還是副本。那麼,在查詢的過程中,一旦指定了感興趣的路由屬性,ES就可以直接到相應的分片所在的機器上進行搜尋,而避免了複雜的分散式協同的一些工作,從而提升了ES的效能。於此同時,假設機器1上存有路由屬性A的文件,機器2上存有路由屬性為B的文件,那麼我在查詢的時候一旦指定目標路由屬性為A,即使機器2故障癱瘓,對機器1構不成很大影響,所以這麼做對災況下的查詢也提出瞭解決方案。所謂的路由,本質上是一個分桶(Bucketing)操作。當然,查詢中也可以指定多個路由屬性,機制大同小異。

7: 新增查詢快取,和預處理查詢  // 測試中

8: 利用磁碟快取提高檢索

磁碟檢索速度過慢,對於實時性較高的場景無法運用磁碟檢索 ;所以索引處理中,需要把索引檔案重新整理載入到快取中 , Elasticsearch預設1s的時間間隔,這也就是說相當於是實時搜尋的,Elasticsearch也提供了單獨的/_reflush介面,使用者如果對1s間隔還是不太滿意,可以主動呼叫介面來保證搜尋可見。

--- 重新整理所有索引
POST /_refresh
--- 指定索引重新整理

  POST /{_index}/_refresh

   一般來說我們會通過/_settings介面或者定製template的方式,加大refresh_interval引數:

--- 禁用自動refresh
PUT /{_index}/_settings{ "refresh_interval": -1 }
--- 設定每秒重新整理
PUT /{_index}/_settings{ "refresh_interval": "1s" }

9:控制translog  

既然refresh只是寫到檔案系統快取中,那麼最後一步寫到實際磁碟又是由什麼來控制的呢?如果這期間發生主機錯誤、硬碟故障等異常情況,資料會不會丟失?這裡,其實Elasticsearch提供了另一個機制來控制。Elasticsearch也把資料寫入到記憶體buffer的同時,其實還另外記錄了一個treanslog的日誌。也就是說,在記憶體資料進入到buffer這一步驟時,其實還另外記錄了一個translog記錄。

10:動態關閉不必要的索引   // 好像沒太大意義

索引預設處於open狀態,處於open狀態的索引都會佔用記憶體,對於不必要的索引可以close

curl -XPOST 'http://localhost:9200/{_index}/_close'

11 : 刪除索引的注意點   // 測試中

當一個文件被更新,舊版本的文件被標記為刪除,新版本的文件在新的段中索引。也許該文件的不同版本都會匹配一個查詢,但是老版本會從結果中刪除,

還是參與查詢,影響檢索效率;

刪除文件在es時時不會馬上刪除,而是先生成.del檔案,es在檢索時會先判斷檔案是否刪除再過濾,這樣會降低檢索效率,可手動執行刪除文件

curl -XPOST 'http://localhost:9200/{_index}/_forcemerge?only_expunge_deletes=true'

12 : 當要匯入大量資料時,設定副本為0,之後動態新增副本   // 效率較大

當匯入大量索引時,設定了副本數,es會同時開啟副本同步,消耗系統資源,同時需要額外提供主副之間的通訊

新建索引是可設定副本為0

----設定副本數

curl -XPOST  'http://localhost:9200/{_index}/_settings' -d

'{"index":{"number_of_replicas":1}}'

13:給檔案系統快取大記憶體  至少給可用記憶體的一半到檔案系統快取。

14: 避免連結,巢狀會使查詢慢幾倍,而親自關係能使查詢慢幾百倍,所以如果同樣的問題可以通過沒有連結的非規範回答就可以提升速度。

15:使用最小的足夠用的數值型別

byte,short,integer,long

half_float,float,double

16: 索引緩衝大小

indices.memory.index_buffer_size通常是JVM的0.1,確保他足夠處理至多512MB的索引。

17:優化es的執行緒池

threadpool.index.type: fixed  

threadpool.index.size: 100  

threadpool.index.queue_size: 500  

18:採用G1垃圾回收機制代替預設CMS

JAVA_OPTS="$JAVA_OPTS -XX:+UseG1GC"  

JAVA_OPTS="$JAVA_OPTS -XX:MaxGCPauseMillis=200"  

19: 清理掉沒用的快取

# 快取型別設定為Soft Reference,只有當記憶體不夠時才會進行回收  

index.cache.field.max_size: 50000  

index.cache.field.expire: 10m  

index.cache.field.type: soft  
---------------------
作者:ailice001
來源:CSDN
原文:https://blog.csdn.net/ailice001/article/details/79664455
版權宣告:本文為博主原創文章,轉載請附上博文連結!