# curl -XPUT localhost:9200/_cluster/settings -d '{ "transient" : { "cluster.routing.allocation.disk.watermark.low" : "85%", "cluster.routing.allocation.disk.watermark.high" : "10gb", "cluster.info.update.interval" : "1m" } }'
# curl -s -XPUT http://127.0.0.1:9200/logstash-2015.05.08/_settings -d '{ "index": { "routing.allocation.total_shards_per_node" : "5" } }'
注意,這裏配置的是 5 而不是 4。由於咱們須要預防有機器故障,分片發生遷移的狀況。若是寫的是 4,那麼分片遷移會失敗。
此外,另外一種方式則更加玄妙,Elasticsearch 中有一系列參數,相互影響,最終聯合決定分片分配:
cluster.routing.allocation.balance.shard 節點上分配分片的權重,默認爲 0.45。數值越大越傾向於在節點層面均衡分片。
cluster.routing.allocation.balance.index 每一個索引往單個節點上分配分片的權重,默認爲 0.55。數值越大越傾向於在索引層面均衡分片。
cluster.routing.allocation.balance.threshold 大於閾值則觸發均衡操做。默認爲1。html
# curl -XPOST 127.0.0.1:9200/_cluster/reroute -d '{ "commands" : [ { "allocate_stale_primary" : { "index" : "logstash-2015.05.27", "shard" : 61, "node" : "10.19.0.77", "accept_data_loss" : true } } ] }'
curl -XPOST 127.0.0.1:9200/_cluster/reroute -d '{ "commands" : [ { "move" : { "index" : "logstash-2015.05.22", "shard" : 0, "from_node" : "10.19.0.81", "to_node" : "10.19.0.104" } } ] }'
curl -XPUT 127.0.0.1:9200/_cluster/settings -d '{ "transient" :{ "cluster.routing.allocation.exclude._ip" : "10.0.0.1" } }'
Elasticsearch 集羣就會自動把這個 IP 上的全部分片,都自動轉移到其餘節點上。等到轉移完成,這個空節點就能夠毫無影響的下線了。和 _ip 相似的參數還有 _host, _name 等。此外,這類參數不單是 cluster 級別,也能夠是 index 級別。下一小節就是 index 級別的用例。node
Elasticsearch 集羣一個比較突出的問題是: 用戶作一次大的查詢的時候, 很是大量的讀 IO 以及聚合計算致使機器 Load 升高, CPU 使用率上升, 會影響阻塞到新數據的寫入, 這個過程甚至會持續幾分鐘。因此,可能須要仿照 MySQL 集羣同樣,作讀寫分離。1算法
實施方案apache
N 臺機器作熱數據的存儲, 上面只放當天的數據。這 N 臺熱數據節點上面的 elasticsearc.yml 中配置 node.tag: hot
以前的數據放在另外的 M 臺機器上。這 M 臺冷數據節點中配置 node.tag: stale
模板中控制對新建索引添加 hot 標籤:
{
「order」 : 0,
「template」 : 「*」,
「settings」 : {
「index.routing.allocation.require.tag」 : 「hot」
}
}
天天計劃任務更新索引的配置, 將 tag 更改成 stale, 索引會自動遷移到 M 臺冷數據節點編程
# curl -XPUT http://127.0.0.1:9200/indexname/_settings -d' { "index": { "routing": { "allocation": { "require": { "tag": "stale" } } } } }'
GC
[垃圾回收]
等緣由會偶爾沒及時響應 ping ,通常建議稍加大 Fault Detection 的超時時間。discovery.zen.ping.unicast.hosts: ["es0","es1", "es2","es3","es4"] # 集羣自動發現 discovery.zen.fd.ping_timeout: 120s # 超時時間(根據實際狀況調整) discovery.zen.fd.ping_retries: 6 # 重試次數,防止GC[Garbage collection]節點不響應被剔除 discovery.zen.fd.ping_interval: 30s # 運行間隔
# curl -XPOST http://127.0.0.1:9200/logstash-2015.06.21/testlog -d '{ "date" : "1434966686000", "user" : "chenlin7", "mesg" : "first message into Elasticsearch" }'
命令返回響應結果爲:api
{"_index":"logstash-2015.06.21","_type":"testlog","_id":"AU4ew3h2nBE6n0qcyVJK","_version":1,"created":true}
# curl -XGET http://127.0.0.1:9200/logstash-2015.06.21/testlog/AU4ew3h2nBE6n0qcyVJK # curl -XGET http://127.0.0.1:9200/logstash-2015.06.21/testlog/AU4ew3h2nBE6n0qcyVJK/_source GET apache-2016.12.30/testlog/AVlPEWLkYdfL4HTWelef/_source GET apache-2016.12.30/testlog/AVlPEWLkYdfL4HTWelef?fields=user # 指定字段
# curl -XDELETE http://127.0.0.1:9200/logstash-2015.06.21/testlog/AU4ew3h2nBE6n0qcyVJK 刪除不單針對單條數據,還能夠刪除整個整個索引。甚至能夠用通配符。 # curl -XDELETE http://127.0.0.1:9200/logstash-2015.06.0* 在 Elasticsearch 2.x 以前,能夠經過查詢語句刪除,也能夠刪除某個 _type 內的數據。如今都已經再也不內置支持,改成 Delete by Query 插件。由於這種方式自己對性能影響較大!
已經寫過的數據,一樣仍是能夠修改的。有兩種辦法,一種是全量提交,即指明 _id 再發送一次寫入請求。
# curl -XPOST http://127.0.0.1:9200/logstash-2015.06.21/testlog/AU4ew3h2nBE6n0qcyVJK -d '{ "date" : "1434966686000", "user" : "chenlin7", "mesg" " "first message into Elasticsearch but version 2" }' 另外一種是局部更新,使用 /_update 接口: # curl -XPOST 'http://127.0.0.1:9200/logstash-2015.06.21/testlog/AU4ew3h2nBE6n0qcyVJK/_update' -d '{ "doc" : { "user" : "someone" } }' 或者 # curl -XPOST 'http://127.0.0.1:9200/logstash-2015.06.21/testlog/AU4ew3h2nBE6n0qcyVJK/_update' -d '{ "script" : "ctx._source.user = \"someone\"" }'
PUT /_cluster/settings{
"transient": { "cluster.routing.allocation.disk.watermark.low": "80%", "cluster.routing.allocation.disk.watermark.high": "5gb", "cluster.info.update.interval": "1m" } }
全文搜索
# curl -XGET http://127.0.0.1:9200/logstash-2015.06.21/testlog/_search?q=first # curl -XGET http://127.0.0.1:9200/logstash-2015.06.21/testlog/_search?q=user:"chenlin7" { "took": 2, Elasticsearch 執行這個搜索的耗時,以毫秒爲單位 "timed_out": false, 搜索是否超時 "_shards": { 指出多少個分片被搜索了,同時也指出了成功/失敗的被搜索的shards 的數量 "total": 5, "successful": 5, "failed": 0 }, "hits" : { 搜索結果 "total" : 579, 匹配查詢條件的文檔的總數目 "max_score" : 0.12633952, "hits" : [ 真正的搜索結果數組(默認是前10個文檔) { "_index" : "logstash-2015.06.21", "_type" : "logs", "_id" : "AVmvfgGaSF0Iy2LFN0EH", "_score" : 0.12633952, "_source" : { "user" : "chenlin7" } } ......
term query 的寫法數組
# curl -XGET http://127.0.0.1:9200/_search -d ' { "query": { "term": { "user": "chenlin7" } } }'
$ curl -XGET 127.0.0.1:9200/_cluster/health?pretty安全
主分片缺失
。這部分數據徹底不可用。而考慮到 ES 在寫入端是簡單的取餘算法,輪到這個分片上的數據也會持續寫入報錯。接口請求的時候,能夠附加一個 level 參數,指定輸出信息以 indices 仍是 shards 級別顯示。固然,通常來講,indices 級別就夠了。bash
對不瞭解 JVM 的 GC 的讀者,這裏先介紹一下 GC(垃圾收集)以及 GC 對 Elasticsearch 的影響。
Java is a garbage-collected language, which means that the programmer does not manually manage memory allocation and deallocation. The programmer simply writes code, and the Java Virtual Machine (JVM) manages the process of allocating memory as needed, and then later cleaning up that memory when no longer needed. Java 是一個自動垃圾收集的編程語言,啓動 JVM 虛擬機的時候,會分配到固定大小的內存塊,這個塊叫作 heap(堆)。JVM 會把 heap 分紅兩個組:
Young 新實例化的對象所分配的空間。這個空間通常來講只有 100MB 到 500MB 大小。Young 空間又分爲兩個 survivor(倖存)空間。當 Young 空間滿,就會發生一次 young gc,還存活的對象,就被移入倖存空間裏,已失效的對象則被移除。
Old 老對象存儲的空間。這些對象應該是長期存活並且在較長一段時間內不會變化的內容。這個空間會大不少,在 ES 來講,一節點上可能就有 30GB 內存是這個空間。前面提到的 young gc 中,若是某個對象連續屢次倖存下來,就會被移進 Old 空間內。而等到 Old 空間滿,就會發生一次 old gc,把失效對象移除。
聽起來很美好的樣子,可是這些都是有代價的!在 GC 發生的時候,JVM 須要暫停程序運行,以便本身追蹤對象圖收集所有失效對象。在這期間,其餘一切都不會繼續運行。請求沒有響應,ping 沒有應答,分片不會分配……
固然,young gc 通常來講執行極快,沒太大影響。可是 old 空間那麼大,稍慢一點的 gc 就意味着程序幾秒乃至十幾秒的不可用,這太危險了。
JVM 自己對 gc 算法一直在努力優化,Elasticsearch 也儘可能複用內部對象,複用網絡緩衝,而後還提供像 Doc Values 這樣的特性。但無論怎麼說,gc 性能老是咱們須要密切關注的數據,由於它是集羣穩定性最大的影響因子。
若是你的 ES 集羣監控裏發現常常有很耗時的 GC,說明集羣負載很重,內存不足。嚴重狀況下,這些 GC 致使節點沒法正確響應集羣之間的 ping ,可能就直接從集羣裏退出了。而後數據分片也隨之在集羣中從新遷移,引起更大的網絡和磁盤 IO,正常的寫入和搜索也會受到影響。服務器
1. 關閉分片自動均衡 PUT /_cluster/settings { "transient" : { "cluster.routing.allocation.enable" : "none" } } 2). 升級重啓該節點,並確認該節點從新加入到了集羣中 3). 其餘節點重複第2步,升級重啓。 4. 最後全部節點配置更新完成後,重啓集羣的shard均衡 curl -XPUT http://192.168.1.2/_cluster/settings -d' { "transient" : { "cluster.routing.allocation.enable" : "all" } }'