在ES中, 要保證被索引的文件能夠立即被搜尋到, 有兩種方法:_refresh 或者_flush。

那麼二者的區別是什麼呢?要搞懂這個問題, 就需要對ES中文件的索引過程有個瞭解。

我們知道ES的索引資料是寫入到磁碟上的。但這個過程是分階段實現的,因為IO的操作是比較費時的。

當一個文件進入ES的初期, 文件是被儲存到記憶體裡的,預設經過1s之後, 會被寫入檔案系統快取,這樣該文件就可以被搜尋到了,注意,此時該索引資料被沒有最終寫入到磁碟上。如果你對這1s的時間間隔還不滿意, 呼叫_refresh就可以立即實現記憶體->檔案系統快取, 從而使文件可以立即被搜尋到。

所以refresh實現的是文件資料從記憶體到檔案系統快取的過程。

再來看flush,flush是用於translog的。

ES為了資料的安全, 在接受寫入的文件的時候, 在寫入記憶體buffer的同時, 會寫一份translog日誌,從而在出現程式故障/磁碟異常時, 保證資料的完整和安全。flush會觸發lucene commit,並清空translog日誌檔案。 translog的flush是ES在後臺自動執行的,預設情況下ES每隔5s會去檢測要不要flush translog,預設條件是:每 30 分鐘主動進行一次 flush,或者當 translog 檔案大小大於 512MB主動進行一次 flush。對應的配置是index.translog.flush_threshold_period 和 index.translog.flush_threshold_size

需要指出的是, 從ES2.0開始,每次 index、bulk、delete、update 完成的時候,一定觸發flush translog 到磁碟上,才給請求返回 200 OK。這個改變提高了資料安全性,但是會對寫入的效能造成不小的影響。在寫入效率優先的情況下,可以在 index template 裡設定如下引數:"index.translog.durability":"async" 和 "index.translog.sync_interval":30s (預設是5s)。

參考:

1. http://stackoverflow.com/questions/19963406/refresh-vs-flush

2.https://www.elastic.co/guide/en/elasticsearch/reference/current/index-modules-translog.html

3. http://kibana.logstash.es/content/elasticsearch/principle/realtime.html